xref: /cloud-hypervisor/devices/src/interrupt_controller.rs (revision 6f8bd27cf7629733582d930519e98d19e90afb16)
1 // Copyright 2020, ARM Limited.
2 //
3 // SPDX-License-Identifier: Apache-2.0 AND BSD-3-Clause
4 
5 use std::io;
6 use std::result;
7 use vmm_sys_util::eventfd::EventFd;
8 
9 #[derive(Debug)]
10 pub enum Error {
11     /// Invalid trigger mode.
12     InvalidTriggerMode,
13     /// Invalid delivery mode.
14     InvalidDeliveryMode,
15     /// Failed creating the interrupt source group.
16     CreateInterruptSourceGroup(io::Error),
17     /// Failed triggering the interrupt.
18     TriggerInterrupt(io::Error),
19     /// Failed masking the interrupt.
20     MaskInterrupt(io::Error),
21     /// Failed unmasking the interrupt.
22     UnmaskInterrupt(io::Error),
23     /// Failed updating the interrupt.
24     UpdateInterrupt(io::Error),
25     /// Failed enabling the interrupt.
26     EnableInterrupt(io::Error),
27     /// Failed creating GIC device.
28     CreateGic(hypervisor::HypervisorVmError),
29 }
30 
31 type Result<T> = result::Result<T, Error>;
32 
33 pub struct MsiMessage {
34     // Message Address Register
35     //   31-20: Base address. Fixed value (0x0FEE)
36     //   19-12: Destination ID
37     //   11-4:  Reserved
38     //   3:     Redirection Hint indication
39     //   2:     Destination Mode
40     //   1-0:   Reserved
41     pub addr: u32,
42     // Message Data Register
43     //   32-16: Reserved
44     //   15:    Trigger Mode. 0 = Edge, 1 = Level
45     //   14:    Level. 0 = Deassert, 1 = Assert
46     //   13-11: Reserved
47     //   10-8:  Delivery Mode
48     //   7-0:   Vector
49     pub data: u32,
50 }
51 
52 // Introduce trait InterruptController to uniform the interrupt
53 // service provided for devices.
54 // Device manager uses this trait without caring whether it is a
55 // IOAPIC (X86) or GIC (Arm).
56 pub trait InterruptController: Send {
57     fn service_irq(&mut self, irq: usize) -> Result<()>;
58     #[cfg(target_arch = "x86_64")]
59     fn end_of_interrupt(&mut self, vec: u8);
60     fn notifier(&self, irq: usize) -> Option<EventFd>;
61 }
62