Generate a MSI interrupt using memory write

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
u9012063
Member
Member
Posts: 26
Joined: Mon Jan 23, 2012 5:00 am
Location: Stony Brook University | ITRI

Generate a MSI interrupt using memory write

Post by u9012063 »

Hey folks,

AFAIK, the MSI/MSI-X allows device to generate an interrupt by writing the message data to an address. Instead of using device, is it possible to generate a fake interrupt by CPU doing a memory write to the same address with the assigned data?

My experiment:
I have a NIC card with the msi address:feeff00c and data: 41a2. So I wrote a kernel module mapping the physical address feeff00c to a virtual address and call iowrite32(virt_addr, 0x41a2) in order to generate an interrupt. From my understanding, this msi address is actually mapped to the CPU local apic and I assume a memory write to it will generate an interrupt to the cpu. I assume if it works, I can see a interrupt is generated from /proc/interrupts. However, no interrupt has been seen. Is calling iowrite(addr, data) to the msi addr the same as device doing the same thing? Otherwise why didn't I see any interrupt using CPU memory write?

My device information:
00:19.0 Ethernet controller: Intel Corporation 82579LM Gigabit Network Connection (rev 05)
Capabilities: [90] MSI: Enable+ Count=1/1 Maskable- 64bit-
Address: feeff00c Data: 41a2

My /proc/iomem
fee00000-fee00fff : Local APIC
ff000000-ffffffff : reserved

Thanks a lot!

--- William
Nable
Member
Member
Posts: 453
Joined: Tue Nov 08, 2011 11:35 am

Re: Generate a MSI interrupt using memory write

Post by Nable »

MSI "address" isn't just an address, it contains some bits with settings. Read more docs about local APIC. And "data" isn't simple data.
Just read `Intel Architecture Software Developer’s Manual, Volume 3A System Programming Guide', chapter 10.11, it's very simple but required to understand MSIs.

And one more thing: don't read/write IO locations directly unless you fully understand what you're doing. It can lead to data loss and/or even hardware damage. Yes, really. (-;
u9012063
Member
Member
Posts: 26
Joined: Mon Jan 23, 2012 5:00 am
Location: Stony Brook University | ITRI

Re: Generate a MSI interrupt using memory write

Post by u9012063 »

Thanks! I've checked my address: 0xfee0100c and data: 41a2

From the IA32 manual:
The address register = 0xfee0100c goes like this:
Bits 31 to 20 = 0xFEE = address is in the local APIC area
Bits 19 to 12 = Destination APIC ID for the IRQ = 1
Bit 3 = RH = Redirection Hint = 1
Bit 2 = DM = Destination Mode (same meaning as for IPIs) = 1
Bits 0 to 1 = Don't care
In my case, RH = DM = 1, From the IA32, "If RH is 1 and DM is 1, the Destination ID Field is interpreted as in logical destination mode and the redirection is limited to only those processors that are part of the logical group of processors based on the processor’s logical APIC ID and the Destination ID field in the message."
How do I know my processor's APIC ID and which redirection mode is used in the current configuration?

The data register = 41aa, goes like this:
Bit 15 = Trigger Mode (edge or level triggered) = 0 edge trigger
Bit 14 = polarity = 1: Assert
Bits 8 to 10 = Delivery mode = 1 = Lowest Priority
Bits 0 to 7 = Interrupt vector = aa
(Lowest Priority) — Deliver the signal to the agent that is executing at the lowest priority of all agents listed in the destination field. The trigger mode can be edge or level.


Regards,
William
User avatar
Brendan
Member
Member
Posts: 8561
Joined: Sat Jan 15, 2005 12:00 am
Location: At his keyboard!
Contact:

Re: Generate a MSI interrupt using memory write

Post by Brendan »

Hi,
u9012063 wrote:AFAIK, the MSI/MSI-X allows device to generate an interrupt by writing the message data to an address. Instead of using device, is it possible to generate a fake interrupt by CPU doing a memory write to the same address with the assigned data?
No.

Writes from the CPU to it's own (internal) local APIC area aren't visible outside that CPU (the CPU handles the writes internally itself). Writes from the bus to the MSI area are intercepted by the chipset or memory controller and converted into "interrupt messages" before any CPU sees them (the CPU only sees the "interrupt messages" and doesn't see writes to the MSI area).

If you want to send an interrupt from one CPU to another (or from one CPU to itself, or from one CPU to a group of CPUs), then use the local APIC to send an IPI (Inter-Processor Interrupt)).


Cheers,

Brendan
For all things; perfection is, and will always remain, impossible to achieve in practice. However; by striving for perfection we create things that are as perfect as practically possible. Let the pursuit of perfection be our guide.
u9012063
Member
Member
Posts: 26
Joined: Mon Jan 23, 2012 5:00 am
Location: Stony Brook University | ITRI

Re: Generate a MSI interrupt using memory write

Post by u9012063 »

Hi Brendan,
Thanks a lot~ very appreciate
William
Post Reply