msi: Add setup/map function
authorSepherosa Ziehau <sephe@dragonflybsd.org>
Sun, 25 Dec 2011 11:46:03 +0000 (19:46 +0800)
committerSepherosa Ziehau <sephe@dragonflybsd.org>
Tue, 27 Dec 2011 05:44:42 +0000 (13:44 +0800)
- msi_setup, setup the IDT entry properly
- msi_map, return the MSI address and MSI data according to the
  'intr' and 'cpuid'

The various MSI macros forming MSI address/data are taken from FreeBSD

sys/platform/pc64/conf/files
sys/platform/pc64/include/msi_var.h [new file with mode: 0644]
sys/platform/pc64/x86_64/msi.c [new file with mode: 0644]

index d1d8183..fbccd6c 100644 (file)
@@ -186,6 +186,7 @@ platform/pc64/x86_64/initcpu.c              standard
 platform/pc64/x86_64/identcpu.c                standard
 platform/pc64/x86_64/amd64_mem.c       standard
 platform/pc64/x86_64/cpufreq_machdep.c    standard
+platform/pc64/x86_64/msi.c             standard
 
 platform/pc64/apic/lapic.c             standard
 platform/pc64/apic/ioapic.c            standard
diff --git a/sys/platform/pc64/include/msi_var.h b/sys/platform/pc64/include/msi_var.h
new file mode 100644 (file)
index 0000000..ea8ca1f
--- /dev/null
@@ -0,0 +1,11 @@
+#ifndef _ARCH_MSI_VAR_H_
+#define _ARCH_MSI_VAR_H_
+
+#ifndef _SYS_TYPES_H_
+#include <sys/types.h>
+#endif
+
+void   msi_setup(int intr, int cpuid);
+void   msi_map(int intr, uint64_t *addr, uint32_t *data, int cpuid);
+
+#endif /* !_ARCH_MSI_VAR_H_ */
diff --git a/sys/platform/pc64/x86_64/msi.c b/sys/platform/pc64/x86_64/msi.c
new file mode 100644 (file)
index 0000000..e2ce7b9
--- /dev/null
@@ -0,0 +1,448 @@
+#include <sys/param.h>
+
+#include <machine/intr_machdep.h>
+#include <machine/msi_machdep.h>
+#include <machine/msi_var.h>
+#include <machine/md_var.h>
+
+#include <machine_base/apic/apicreg.h>
+#include <machine_base/apic/lapic.h>
+
+/* MSI address */
+#define        MSI_X86_ADDR_DEST               0x000ff000
+#define        MSI_X86_ADDR_RH                 0x00000008
+# define MSI_X86_ADDR_RH_ON            0x00000008
+# define MSI_X86_ADDR_RH_OFF           0x00000000
+#define        MSI_X86_ADDR_DM                 0x00000004
+# define MSI_X86_ADDR_DM_PHYSICAL      0x00000000
+# define MSI_X86_ADDR_DM_LOGICAL       0x00000004
+
+/* MSI data */
+#define        MSI_X86_DATA_TRGRMOD            IOART_TRGRMOD   /* Trigger mode. */
+# define MSI_X86_DATA_TRGREDG          IOART_TRGREDG
+# define MSI_X86_DATA_TRGRLVL          IOART_TRGRLVL
+#define        MSI_X86_DATA_LEVEL              0x00004000      /* Polarity. */
+# define MSI_X86_DATA_DEASSERT         0x00000000
+# define MSI_X86_DATA_ASSERT           0x00004000
+#define        MSI_X86_DATA_DELMOD             IOART_DELMOD    /* Delivery mode. */
+# define MSI_X86_DATA_DELFIXED         IOART_DELFIXED
+# define MSI_X86_DATA_DELLOPRI         IOART_DELLOPRI
+# define MSI_X86_DATA_DELSMI           IOART_DELSMI
+# define MSI_X86_DATA_DELNMI           IOART_DELNMI
+# define MSI_X86_DATA_DELINIT          IOART_DELINIT
+# define MSI_X86_DATA_DELEXINT         IOART_DELEXINT
+#define        MSI_X86_DATA_INTVEC             IOART_INTVEC    /* Interrupt vector. */
+
+#define        MSI_X86_ADDR(lapic_id) \
+       (MSI_X86_ADDR_BASE | (lapic_id) << 12 | \
+        MSI_X86_ADDR_RH_OFF | MSI_X86_ADDR_DM_PHYSICAL)
+#define        MSI_X86_DATA(vector) \
+       (MSI_X86_DATA_TRGREDG | MSI_X86_DATA_DELFIXED | (vector))
+
+extern inthand_t
+       IDTVEC(msi_intr0),
+       IDTVEC(msi_intr1),
+       IDTVEC(msi_intr2),
+       IDTVEC(msi_intr3),
+       IDTVEC(msi_intr4),
+       IDTVEC(msi_intr5),
+       IDTVEC(msi_intr6),
+       IDTVEC(msi_intr7),
+       IDTVEC(msi_intr8),
+       IDTVEC(msi_intr9),
+       IDTVEC(msi_intr10),
+       IDTVEC(msi_intr11),
+       IDTVEC(msi_intr12),
+       IDTVEC(msi_intr13),
+       IDTVEC(msi_intr14),
+       IDTVEC(msi_intr15),
+       IDTVEC(msi_intr16),
+       IDTVEC(msi_intr17),
+       IDTVEC(msi_intr18),
+       IDTVEC(msi_intr19),
+       IDTVEC(msi_intr20),
+       IDTVEC(msi_intr21),
+       IDTVEC(msi_intr22),
+       IDTVEC(msi_intr23),
+       IDTVEC(msi_intr24),
+       IDTVEC(msi_intr25),
+       IDTVEC(msi_intr26),
+       IDTVEC(msi_intr27),
+       IDTVEC(msi_intr28),
+       IDTVEC(msi_intr29),
+       IDTVEC(msi_intr30),
+       IDTVEC(msi_intr31),
+       IDTVEC(msi_intr32),
+       IDTVEC(msi_intr33),
+       IDTVEC(msi_intr34),
+       IDTVEC(msi_intr35),
+       IDTVEC(msi_intr36),
+       IDTVEC(msi_intr37),
+       IDTVEC(msi_intr38),
+       IDTVEC(msi_intr39),
+       IDTVEC(msi_intr40),
+       IDTVEC(msi_intr41),
+       IDTVEC(msi_intr42),
+       IDTVEC(msi_intr43),
+       IDTVEC(msi_intr44),
+       IDTVEC(msi_intr45),
+       IDTVEC(msi_intr46),
+       IDTVEC(msi_intr47),
+       IDTVEC(msi_intr48),
+       IDTVEC(msi_intr49),
+       IDTVEC(msi_intr50),
+       IDTVEC(msi_intr51),
+       IDTVEC(msi_intr52),
+       IDTVEC(msi_intr53),
+       IDTVEC(msi_intr54),
+       IDTVEC(msi_intr55),
+       IDTVEC(msi_intr56),
+       IDTVEC(msi_intr57),
+       IDTVEC(msi_intr58),
+       IDTVEC(msi_intr59),
+       IDTVEC(msi_intr60),
+       IDTVEC(msi_intr61),
+       IDTVEC(msi_intr62),
+       IDTVEC(msi_intr63),
+       IDTVEC(msi_intr64),
+       IDTVEC(msi_intr65),
+       IDTVEC(msi_intr66),
+       IDTVEC(msi_intr67),
+       IDTVEC(msi_intr68),
+       IDTVEC(msi_intr69),
+       IDTVEC(msi_intr70),
+       IDTVEC(msi_intr71),
+       IDTVEC(msi_intr72),
+       IDTVEC(msi_intr73),
+       IDTVEC(msi_intr74),
+       IDTVEC(msi_intr75),
+       IDTVEC(msi_intr76),
+       IDTVEC(msi_intr77),
+       IDTVEC(msi_intr78),
+       IDTVEC(msi_intr79),
+       IDTVEC(msi_intr80),
+       IDTVEC(msi_intr81),
+       IDTVEC(msi_intr82),
+       IDTVEC(msi_intr83),
+       IDTVEC(msi_intr84),
+       IDTVEC(msi_intr85),
+       IDTVEC(msi_intr86),
+       IDTVEC(msi_intr87),
+       IDTVEC(msi_intr88),
+       IDTVEC(msi_intr89),
+       IDTVEC(msi_intr90),
+       IDTVEC(msi_intr91),
+       IDTVEC(msi_intr92),
+       IDTVEC(msi_intr93),
+       IDTVEC(msi_intr94),
+       IDTVEC(msi_intr95),
+       IDTVEC(msi_intr96),
+       IDTVEC(msi_intr97),
+       IDTVEC(msi_intr98),
+       IDTVEC(msi_intr99),
+       IDTVEC(msi_intr100),
+       IDTVEC(msi_intr101),
+       IDTVEC(msi_intr102),
+       IDTVEC(msi_intr103),
+       IDTVEC(msi_intr104),
+       IDTVEC(msi_intr105),
+       IDTVEC(msi_intr106),
+       IDTVEC(msi_intr107),
+       IDTVEC(msi_intr108),
+       IDTVEC(msi_intr109),
+       IDTVEC(msi_intr110),
+       IDTVEC(msi_intr111),
+       IDTVEC(msi_intr112),
+       IDTVEC(msi_intr113),
+       IDTVEC(msi_intr114),
+       IDTVEC(msi_intr115),
+       IDTVEC(msi_intr116),
+       IDTVEC(msi_intr117),
+       IDTVEC(msi_intr118),
+       IDTVEC(msi_intr119),
+       IDTVEC(msi_intr120),
+       IDTVEC(msi_intr121),
+       IDTVEC(msi_intr122),
+       IDTVEC(msi_intr123),
+       IDTVEC(msi_intr124),
+       IDTVEC(msi_intr125),
+       IDTVEC(msi_intr126),
+       IDTVEC(msi_intr127),
+       IDTVEC(msi_intr128),
+       IDTVEC(msi_intr129),
+       IDTVEC(msi_intr130),
+       IDTVEC(msi_intr131),
+       IDTVEC(msi_intr132),
+       IDTVEC(msi_intr133),
+       IDTVEC(msi_intr134),
+       IDTVEC(msi_intr135),
+       IDTVEC(msi_intr136),
+       IDTVEC(msi_intr137),
+       IDTVEC(msi_intr138),
+       IDTVEC(msi_intr139),
+       IDTVEC(msi_intr140),
+       IDTVEC(msi_intr141),
+       IDTVEC(msi_intr142),
+       IDTVEC(msi_intr143),
+       IDTVEC(msi_intr144),
+       IDTVEC(msi_intr145),
+       IDTVEC(msi_intr146),
+       IDTVEC(msi_intr147),
+       IDTVEC(msi_intr148),
+       IDTVEC(msi_intr149),
+       IDTVEC(msi_intr150),
+       IDTVEC(msi_intr151),
+       IDTVEC(msi_intr152),
+       IDTVEC(msi_intr153),
+       IDTVEC(msi_intr154),
+       IDTVEC(msi_intr155),
+       IDTVEC(msi_intr156),
+       IDTVEC(msi_intr157),
+       IDTVEC(msi_intr158),
+       IDTVEC(msi_intr159),
+       IDTVEC(msi_intr160),
+       IDTVEC(msi_intr161),
+       IDTVEC(msi_intr162),
+       IDTVEC(msi_intr163),
+       IDTVEC(msi_intr164),
+       IDTVEC(msi_intr165),
+       IDTVEC(msi_intr166),
+       IDTVEC(msi_intr167),
+       IDTVEC(msi_intr168),
+       IDTVEC(msi_intr169),
+       IDTVEC(msi_intr170),
+       IDTVEC(msi_intr171),
+       IDTVEC(msi_intr172),
+       IDTVEC(msi_intr173),
+       IDTVEC(msi_intr174),
+       IDTVEC(msi_intr175),
+       IDTVEC(msi_intr176),
+       IDTVEC(msi_intr177),
+       IDTVEC(msi_intr178),
+       IDTVEC(msi_intr179),
+       IDTVEC(msi_intr180),
+       IDTVEC(msi_intr181),
+       IDTVEC(msi_intr182),
+       IDTVEC(msi_intr183),
+       IDTVEC(msi_intr184),
+       IDTVEC(msi_intr185),
+       IDTVEC(msi_intr186),
+       IDTVEC(msi_intr187),
+       IDTVEC(msi_intr188),
+       IDTVEC(msi_intr189),
+       IDTVEC(msi_intr190),
+       IDTVEC(msi_intr191);
+
+static inthand_t *msi_intr[IDT_HWI_VECTORS] = {
+       &IDTVEC(msi_intr0),
+       &IDTVEC(msi_intr1),
+       &IDTVEC(msi_intr2),
+       &IDTVEC(msi_intr3),
+       &IDTVEC(msi_intr4),
+       &IDTVEC(msi_intr5),
+       &IDTVEC(msi_intr6),
+       &IDTVEC(msi_intr7),
+       &IDTVEC(msi_intr8),
+       &IDTVEC(msi_intr9),
+       &IDTVEC(msi_intr10),
+       &IDTVEC(msi_intr11),
+       &IDTVEC(msi_intr12),
+       &IDTVEC(msi_intr13),
+       &IDTVEC(msi_intr14),
+       &IDTVEC(msi_intr15),
+       &IDTVEC(msi_intr16),
+       &IDTVEC(msi_intr17),
+       &IDTVEC(msi_intr18),
+       &IDTVEC(msi_intr19),
+       &IDTVEC(msi_intr20),
+       &IDTVEC(msi_intr21),
+       &IDTVEC(msi_intr22),
+       &IDTVEC(msi_intr23),
+       &IDTVEC(msi_intr24),
+       &IDTVEC(msi_intr25),
+       &IDTVEC(msi_intr26),
+       &IDTVEC(msi_intr27),
+       &IDTVEC(msi_intr28),
+       &IDTVEC(msi_intr29),
+       &IDTVEC(msi_intr30),
+       &IDTVEC(msi_intr31),
+       &IDTVEC(msi_intr32),
+       &IDTVEC(msi_intr33),
+       &IDTVEC(msi_intr34),
+       &IDTVEC(msi_intr35),
+       &IDTVEC(msi_intr36),
+       &IDTVEC(msi_intr37),
+       &IDTVEC(msi_intr38),
+       &IDTVEC(msi_intr39),
+       &IDTVEC(msi_intr40),
+       &IDTVEC(msi_intr41),
+       &IDTVEC(msi_intr42),
+       &IDTVEC(msi_intr43),
+       &IDTVEC(msi_intr44),
+       &IDTVEC(msi_intr45),
+       &IDTVEC(msi_intr46),
+       &IDTVEC(msi_intr47),
+       &IDTVEC(msi_intr48),
+       &IDTVEC(msi_intr49),
+       &IDTVEC(msi_intr50),
+       &IDTVEC(msi_intr51),
+       &IDTVEC(msi_intr52),
+       &IDTVEC(msi_intr53),
+       &IDTVEC(msi_intr54),
+       &IDTVEC(msi_intr55),
+       &IDTVEC(msi_intr56),
+       &IDTVEC(msi_intr57),
+       &IDTVEC(msi_intr58),
+       &IDTVEC(msi_intr59),
+       &IDTVEC(msi_intr60),
+       &IDTVEC(msi_intr61),
+       &IDTVEC(msi_intr62),
+       &IDTVEC(msi_intr63),
+       &IDTVEC(msi_intr64),
+       &IDTVEC(msi_intr65),
+       &IDTVEC(msi_intr66),
+       &IDTVEC(msi_intr67),
+       &IDTVEC(msi_intr68),
+       &IDTVEC(msi_intr69),
+       &IDTVEC(msi_intr70),
+       &IDTVEC(msi_intr71),
+       &IDTVEC(msi_intr72),
+       &IDTVEC(msi_intr73),
+       &IDTVEC(msi_intr74),
+       &IDTVEC(msi_intr75),
+       &IDTVEC(msi_intr76),
+       &IDTVEC(msi_intr77),
+       &IDTVEC(msi_intr78),
+       &IDTVEC(msi_intr79),
+       &IDTVEC(msi_intr80),
+       &IDTVEC(msi_intr81),
+       &IDTVEC(msi_intr82),
+       &IDTVEC(msi_intr83),
+       &IDTVEC(msi_intr84),
+       &IDTVEC(msi_intr85),
+       &IDTVEC(msi_intr86),
+       &IDTVEC(msi_intr87),
+       &IDTVEC(msi_intr88),
+       &IDTVEC(msi_intr89),
+       &IDTVEC(msi_intr90),
+       &IDTVEC(msi_intr91),
+       &IDTVEC(msi_intr92),
+       &IDTVEC(msi_intr93),
+       &IDTVEC(msi_intr94),
+       &IDTVEC(msi_intr95),
+       &IDTVEC(msi_intr96),
+       &IDTVEC(msi_intr97),
+       &IDTVEC(msi_intr98),
+       &IDTVEC(msi_intr99),
+       &IDTVEC(msi_intr100),
+       &IDTVEC(msi_intr101),
+       &IDTVEC(msi_intr102),
+       &IDTVEC(msi_intr103),
+       &IDTVEC(msi_intr104),
+       &IDTVEC(msi_intr105),
+       &IDTVEC(msi_intr106),
+       &IDTVEC(msi_intr107),
+       &IDTVEC(msi_intr108),
+       &IDTVEC(msi_intr109),
+       &IDTVEC(msi_intr110),
+       &IDTVEC(msi_intr111),
+       &IDTVEC(msi_intr112),
+       &IDTVEC(msi_intr113),
+       &IDTVEC(msi_intr114),
+       &IDTVEC(msi_intr115),
+       &IDTVEC(msi_intr116),
+       &IDTVEC(msi_intr117),
+       &IDTVEC(msi_intr118),
+       &IDTVEC(msi_intr119),
+       &IDTVEC(msi_intr120),
+       &IDTVEC(msi_intr121),
+       &IDTVEC(msi_intr122),
+       &IDTVEC(msi_intr123),
+       &IDTVEC(msi_intr124),
+       &IDTVEC(msi_intr125),
+       &IDTVEC(msi_intr126),
+       &IDTVEC(msi_intr127),
+       &IDTVEC(msi_intr128),
+       &IDTVEC(msi_intr129),
+       &IDTVEC(msi_intr130),
+       &IDTVEC(msi_intr131),
+       &IDTVEC(msi_intr132),
+       &IDTVEC(msi_intr133),
+       &IDTVEC(msi_intr134),
+       &IDTVEC(msi_intr135),
+       &IDTVEC(msi_intr136),
+       &IDTVEC(msi_intr137),
+       &IDTVEC(msi_intr138),
+       &IDTVEC(msi_intr139),
+       &IDTVEC(msi_intr140),
+       &IDTVEC(msi_intr141),
+       &IDTVEC(msi_intr142),
+       &IDTVEC(msi_intr143),
+       &IDTVEC(msi_intr144),
+       &IDTVEC(msi_intr145),
+       &IDTVEC(msi_intr146),
+       &IDTVEC(msi_intr147),
+       &IDTVEC(msi_intr148),
+       &IDTVEC(msi_intr149),
+       &IDTVEC(msi_intr150),
+       &IDTVEC(msi_intr151),
+       &IDTVEC(msi_intr152),
+       &IDTVEC(msi_intr153),
+       &IDTVEC(msi_intr154),
+       &IDTVEC(msi_intr155),
+       &IDTVEC(msi_intr156),
+       &IDTVEC(msi_intr157),
+       &IDTVEC(msi_intr158),
+       &IDTVEC(msi_intr159),
+       &IDTVEC(msi_intr160),
+       &IDTVEC(msi_intr161),
+       &IDTVEC(msi_intr162),
+       &IDTVEC(msi_intr163),
+       &IDTVEC(msi_intr164),
+       &IDTVEC(msi_intr165),
+       &IDTVEC(msi_intr166),
+       &IDTVEC(msi_intr167),
+       &IDTVEC(msi_intr168),
+       &IDTVEC(msi_intr169),
+       &IDTVEC(msi_intr170),
+       &IDTVEC(msi_intr171),
+       &IDTVEC(msi_intr172),
+       &IDTVEC(msi_intr173),
+       &IDTVEC(msi_intr174),
+       &IDTVEC(msi_intr175),
+       &IDTVEC(msi_intr176),
+       &IDTVEC(msi_intr177),
+       &IDTVEC(msi_intr178),
+       &IDTVEC(msi_intr179),
+       &IDTVEC(msi_intr180),
+       &IDTVEC(msi_intr181),
+       &IDTVEC(msi_intr182),
+       &IDTVEC(msi_intr183),
+       &IDTVEC(msi_intr184),
+       &IDTVEC(msi_intr185),
+       &IDTVEC(msi_intr186),
+       &IDTVEC(msi_intr187),
+       &IDTVEC(msi_intr188),
+       &IDTVEC(msi_intr189),
+       &IDTVEC(msi_intr190),
+       &IDTVEC(msi_intr191)
+};
+
+void
+msi_setup(int intr, int cpuid)
+{
+       setidt(IDT_OFFSET + intr, msi_intr[intr],
+           SDT_SYSIGT, SEL_KPL, 0, cpuid);
+}
+
+void
+msi_map(int intr, uint64_t *addr, uint32_t *data, int cpuid)
+{
+       int vector, lapic_id;
+
+       vector = IDT_OFFSET + intr;
+       lapic_id = CPUID_TO_APICID(cpuid);
+
+       *addr = MSI_X86_ADDR(lapic_id);
+       *data = MSI_X86_DATA(vector);
+}