source: mainline/kernel/arch/ia32/include/smp/apic.h@ 49e6c6b4

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since 49e6c6b4 was 49e6c6b4, checked in by Adam Hraska <adam.hraska+hos@…>, 13 years ago

ipi: Added support for unicast IPI on amd64, ia32.

  • Property mode set to 100644
File size: 10.5 KB
RevLine 
[f761f1eb]1/*
[df4ed85]2 * Copyright (c) 2001-2004 Jakub Jermar
[f761f1eb]3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 *
9 * - Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * - Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * - The name of the author may not be used to endorse or promote products
15 * derived from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
[da1bafb]29/** @addtogroup ia32
[b45c443]30 * @{
31 */
32/** @file
33 */
34
[06e1e95]35#ifndef KERN_ia32_APIC_H_
36#define KERN_ia32_APIC_H_
[f761f1eb]37
[d99c1d2]38#include <typedefs.h>
[f761f1eb]39#include <cpu.h>
40
[da1bafb]41#define FIXED (0 << 0)
42#define LOPRI (1 << 0)
[f761f1eb]43
[da1bafb]44#define APIC_ID_COUNT 16
[9149135]45
[f761f1eb]46/* local APIC macros */
[da1bafb]47#define IPI_INIT 0
48#define IPI_STARTUP 0
[f761f1eb]49
[8418c7d]50/** Delivery modes. */
[dc0b964]51#define DELMOD_FIXED 0x0U
52#define DELMOD_LOWPRI 0x1U
53#define DELMOD_SMI 0x2U
[8418c7d]54/* 0x3 reserved */
[dc0b964]55#define DELMOD_NMI 0x4U
56#define DELMOD_INIT 0x5U
57#define DELMOD_STARTUP 0x6U
58#define DELMOD_EXTINT 0x7U
[8418c7d]59
60/** Destination modes. */
[dc0b964]61#define DESTMOD_PHYS 0x0U
62#define DESTMOD_LOGIC 0x1U
[8418c7d]63
64/** Trigger Modes. */
[dc0b964]65#define TRIGMOD_EDGE 0x0U
66#define TRIGMOD_LEVEL 0x1U
[8418c7d]67
68/** Levels. */
[dc0b964]69#define LEVEL_DEASSERT 0x0U
70#define LEVEL_ASSERT 0x1U
[8418c7d]71
72/** Destination Shorthands. */
[dc0b964]73#define SHORTHAND_NONE 0x0U
74#define SHORTHAND_SELF 0x1U
75#define SHORTHAND_ALL_INCL 0x2U
76#define SHORTHAND_ALL_EXCL 0x3U
[8418c7d]77
78/** Interrupt Input Pin Polarities. */
[dc0b964]79#define POLARITY_HIGH 0x0U
80#define POLARITY_LOW 0x1U
[f761f1eb]81
[f701b236]82/** Divide Values. (Bit 2 is always 0) */
[dc0b964]83#define DIVIDE_2 0x0U
84#define DIVIDE_4 0x1U
85#define DIVIDE_8 0x2U
86#define DIVIDE_16 0x3U
87#define DIVIDE_32 0x8U
88#define DIVIDE_64 0x9U
89#define DIVIDE_128 0xaU
90#define DIVIDE_1 0xbU
[f701b236]91
92/** Timer Modes. */
[dc0b964]93#define TIMER_ONESHOT 0x0U
94#define TIMER_PERIODIC 0x1U
[f701b236]95
[9149135]96/** Delivery status. */
[dc0b964]97#define DELIVS_IDLE 0x0U
98#define DELIVS_PENDING 0x1U
[9149135]99
100/** Destination masks. */
[dc0b964]101#define DEST_ALL 0xffU
[f761f1eb]102
[93e90c7]103/** Dest format models. */
[dc0b964]104#define MODEL_FLAT 0xfU
105#define MODEL_CLUSTER 0x0U
[93e90c7]106
[8418c7d]107/** Interrupt Command Register. */
[dc0b964]108#define ICRlo (0x300U / sizeof(uint32_t))
109#define ICRhi (0x310U / sizeof(uint32_t))
[da1bafb]110
[b3f8fb7]111typedef struct {
[8418c7d]112 union {
[7f1c620]113 uint32_t lo;
[8418c7d]114 struct {
[da1bafb]115 uint8_t vector; /**< Interrupt Vector. */
116 unsigned int delmod : 3; /**< Delivery Mode. */
117 unsigned int destmod : 1; /**< Destination Mode. */
118 unsigned int delivs : 1; /**< Delivery status (RO). */
119 unsigned int : 1; /**< Reserved. */
120 unsigned int level : 1; /**< Level. */
121 unsigned int trigger_mode : 1; /**< Trigger Mode. */
122 unsigned int : 2; /**< Reserved. */
123 unsigned int shorthand : 2; /**< Destination Shorthand. */
124 unsigned int : 12; /**< Reserved. */
[8418c7d]125 } __attribute__ ((packed));
126 };
127 union {
[7f1c620]128 uint32_t hi;
[8418c7d]129 struct {
[da1bafb]130 unsigned int : 24; /**< Reserved. */
131 uint8_t dest; /**< Destination field. */
[8418c7d]132 } __attribute__ ((packed));
133 };
[b3f8fb7]134} __attribute__ ((packed)) icr_t;
[f761f1eb]135
[11928d5]136/* End Of Interrupt. */
[dc0b964]137#define EOI (0x0b0U / sizeof(uint32_t))
[f761f1eb]138
[f701b236]139/** Error Status Register. */
[dc0b964]140#define ESR (0x280U / sizeof(uint32_t))
[da1bafb]141
[b3f8fb7]142typedef union {
[7f1c620]143 uint32_t value;
144 uint8_t err_bitmap;
[f701b236]145 struct {
[da1bafb]146 unsigned int send_checksum_error : 1;
147 unsigned int receive_checksum_error : 1;
148 unsigned int send_accept_error : 1;
149 unsigned int receive_accept_error : 1;
150 unsigned int : 1;
151 unsigned int send_illegal_vector : 1;
152 unsigned int received_illegal_vector : 1;
153 unsigned int illegal_register_address : 1;
154 unsigned int : 24;
[f701b236]155 } __attribute__ ((packed));
[b3f8fb7]156} esr_t;
[f761f1eb]157
158/* Task Priority Register */
[dc0b964]159#define TPR (0x080U / sizeof(uint32_t))
[da1bafb]160
[b3f8fb7]161typedef union {
[7f1c620]162 uint32_t value;
[d0780b4c]163 struct {
[da1bafb]164 unsigned int pri_sc : 4; /**< Task Priority Sub-Class. */
165 unsigned int pri : 4; /**< Task Priority. */
[d0780b4c]166 } __attribute__ ((packed));
[b3f8fb7]167} tpr_t;
[f761f1eb]168
[8418c7d]169/** Spurious-Interrupt Vector Register. */
[dc0b964]170#define SVR (0x0f0U / sizeof(uint32_t))
[da1bafb]171
[b3f8fb7]172typedef union {
[7f1c620]173 uint32_t value;
[8418c7d]174 struct {
[da1bafb]175 uint8_t vector; /**< Spurious Vector. */
176 unsigned int lapic_enabled : 1; /**< APIC Software Enable/Disable. */
177 unsigned int focus_checking : 1; /**< Focus Processor Checking. */
178 unsigned int : 22; /**< Reserved. */
[8418c7d]179 } __attribute__ ((packed));
[b3f8fb7]180} svr_t;
[f761f1eb]181
[f701b236]182/** Time Divide Configuration Register. */
[dc0b964]183#define TDCR (0x3e0U / sizeof(uint32_t))
[da1bafb]184
[b3f8fb7]185typedef union {
[7f1c620]186 uint32_t value;
[f701b236]187 struct {
[da1bafb]188 unsigned int div_value : 4; /**< Divide Value, bit 2 is always 0. */
189 unsigned int : 28; /**< Reserved. */
[f701b236]190 } __attribute__ ((packed));
[b3f8fb7]191} tdcr_t;
[f761f1eb]192
193/* Initial Count Register for Timer */
[dc0b964]194#define ICRT (0x380U / sizeof(uint32_t))
[f761f1eb]195
196/* Current Count Register for Timer */
[dc0b964]197#define CCRT (0x390U / sizeof(uint32_t))
[f761f1eb]198
[8418c7d]199/** LVT Timer register. */
[dc0b964]200#define LVT_Tm (0x320U / sizeof(uint32_t))
[da1bafb]201
[b3f8fb7]202typedef union {
[7f1c620]203 uint32_t value;
[8418c7d]204 struct {
[da1bafb]205 uint8_t vector; /**< Local Timer Interrupt vector. */
206 unsigned int : 4; /**< Reserved. */
207 unsigned int delivs : 1; /**< Delivery status (RO). */
208 unsigned int : 3; /**< Reserved. */
209 unsigned int masked : 1; /**< Interrupt Mask. */
210 unsigned int mode : 1; /**< Timer Mode. */
211 unsigned int : 14; /**< Reserved. */
[8418c7d]212 } __attribute__ ((packed));
[b3f8fb7]213} lvt_tm_t;
[8418c7d]214
215/** LVT LINT registers. */
[dc0b964]216#define LVT_LINT0 (0x350U / sizeof(uint32_t))
217#define LVT_LINT1 (0x360U / sizeof(uint32_t))
[da1bafb]218
[b3f8fb7]219typedef union {
[7f1c620]220 uint32_t value;
[8418c7d]221 struct {
[da1bafb]222 uint8_t vector; /**< LINT Interrupt vector. */
223 unsigned int delmod : 3; /**< Delivery Mode. */
224 unsigned int : 1; /**< Reserved. */
225 unsigned int delivs : 1; /**< Delivery status (RO). */
226 unsigned int intpol : 1; /**< Interrupt Input Pin Polarity. */
227 unsigned int irr : 1; /**< Remote IRR (RO). */
228 unsigned int trigger_mode : 1; /**< Trigger Mode. */
229 unsigned int masked : 1; /**< Interrupt Mask. */
230 unsigned int : 15; /**< Reserved. */
[8418c7d]231 } __attribute__ ((packed));
[b3f8fb7]232} lvt_lint_t;
[8418c7d]233
234/** LVT Error register. */
[dc0b964]235#define LVT_Err (0x370U / sizeof(uint32_t))
[da1bafb]236
[b3f8fb7]237typedef union {
[7f1c620]238 uint32_t value;
[8418c7d]239 struct {
[da1bafb]240 uint8_t vector; /**< Local Timer Interrupt vector. */
241 unsigned int : 4; /**< Reserved. */
242 unsigned int delivs : 1; /**< Delivery status (RO). */
243 unsigned int : 3; /**< Reserved. */
244 unsigned int masked : 1; /**< Interrupt Mask. */
245 unsigned int : 15; /**< Reserved. */
[8418c7d]246 } __attribute__ ((packed));
[b3f8fb7]247} lvt_error_t;
[8418c7d]248
[f701b236]249/** Local APIC ID Register. */
[dc0b964]250#define L_APIC_ID (0x020U / sizeof(uint32_t))
[da1bafb]251
[b3f8fb7]252typedef union {
[7f1c620]253 uint32_t value;
[f701b236]254 struct {
[da1bafb]255 unsigned int : 24; /**< Reserved. */
256 uint8_t apic_id; /**< Local APIC ID. */
[f701b236]257 } __attribute__ ((packed));
[b3f8fb7]258} l_apic_id_t;
[f761f1eb]259
[11928d5]260/** Local APIC Version Register */
[dc0b964]261#define LAVR (0x030U / sizeof(uint32_t))
262#define LAVR_Mask 0xffU
[da1bafb]263
[dc0b964]264#define is_local_apic(x) (((x) & LAVR_Mask & 0xf0U) == 0x1U)
265#define is_82489DX_apic(x) ((((x) & LAVR_Mask & 0xf0U) == 0x0U))
266#define is_local_xapic(x) (((x) & LAVR_Mask) == 0x14U)
[c9b8c5c]267
[93e90c7]268/** Logical Destination Register. */
[dc0b964]269#define LDR (0x0d0U / sizeof(uint32_t))
[da1bafb]270
[b3f8fb7]271typedef union {
[7f1c620]272 uint32_t value;
[93e90c7]273 struct {
[da1bafb]274 unsigned int : 24; /**< Reserved. */
275 uint8_t id; /**< Logical APIC ID. */
[93e90c7]276 } __attribute__ ((packed));
[b3f8fb7]277} ldr_t;
[93e90c7]278
279/** Destination Format Register. */
[dc0b964]280#define DFR (0x0e0U / sizeof(uint32_t))
[da1bafb]281
[b3f8fb7]282typedef union {
[7f1c620]283 uint32_t value;
[93e90c7]284 struct {
[da1bafb]285 unsigned int : 28; /**< Reserved, all ones. */
286 unsigned int model : 4; /**< Model. */
[93e90c7]287 } __attribute__ ((packed));
[b3f8fb7]288} dfr_t;
[93e90c7]289
[f761f1eb]290/* IO APIC */
[dc0b964]291#define IOREGSEL (0x00U / sizeof(uint32_t))
292#define IOWIN (0x10U / sizeof(uint32_t))
[f761f1eb]293
[dc0b964]294#define IOAPICID 0x00U
295#define IOAPICVER 0x01U
296#define IOAPICARB 0x02U
297#define IOREDTBL 0x10U
[f761f1eb]298
[f701b236]299/** I/O Register Select Register. */
[b3f8fb7]300typedef union {
[7f1c620]301 uint32_t value;
[f701b236]302 struct {
[da1bafb]303 uint8_t reg_addr; /**< APIC Register Address. */
304 unsigned int : 24; /**< Reserved. */
[f701b236]305 } __attribute__ ((packed));
[b3f8fb7]306} io_regsel_t;
[f701b236]307
[a83a802]308/** I/O Redirection Register. */
[b3f8fb7]309typedef struct io_redirection_reg {
[a83a802]310 union {
[7f1c620]311 uint32_t lo;
[a83a802]312 struct {
[da1bafb]313 uint8_t intvec; /**< Interrupt Vector. */
314 unsigned int delmod : 3; /**< Delivery Mode. */
315 unsigned int destmod : 1; /**< Destination mode. */
316 unsigned int delivs : 1; /**< Delivery status (RO). */
317 unsigned int intpol : 1; /**< Interrupt Input Pin Polarity. */
318 unsigned int irr : 1; /**< Remote IRR (RO). */
319 unsigned int trigger_mode : 1; /**< Trigger Mode. */
320 unsigned int masked : 1; /**< Interrupt Mask. */
321 unsigned int : 15; /**< Reserved. */
[8418c7d]322 } __attribute__ ((packed));
[a83a802]323 };
324 union {
[7f1c620]325 uint32_t hi;
[a83a802]326 struct {
[da1bafb]327 unsigned int : 24; /**< Reserved. */
328 uint8_t dest : 8; /**< Destination Field. */
[8418c7d]329 } __attribute__ ((packed));
[a83a802]330 };
331
[b3f8fb7]332} __attribute__ ((packed)) io_redirection_reg_t;
[f761f1eb]333
[9149135]334
335/** IO APIC Identification Register. */
[b3f8fb7]336typedef union {
[7f1c620]337 uint32_t value;
[9149135]338 struct {
[da1bafb]339 unsigned int : 24; /**< Reserved. */
340 unsigned int apic_id : 4; /**< IO APIC ID. */
341 unsigned int : 4; /**< Reserved. */
[9149135]342 } __attribute__ ((packed));
[b3f8fb7]343} io_apic_id_t;
[9149135]344
[7f1c620]345extern volatile uint32_t *l_apic;
346extern volatile uint32_t *io_apic;
[f761f1eb]347
[7f1c620]348extern uint32_t apic_id_mask;
[99718a2e]349extern uint8_t bsp_l_apic;
[f761f1eb]350
351extern void apic_init(void);
352
353extern void l_apic_init(void);
354extern void l_apic_eoi(void);
[49e6c6b4]355extern int l_apic_send_custom_ipi(uint8_t, uint8_t);
[da1bafb]356extern int l_apic_broadcast_custom_ipi(uint8_t);
357extern int l_apic_send_init_ipi(uint8_t);
[f761f1eb]358extern void l_apic_debug(void);
359
[da1bafb]360extern uint32_t io_apic_read(uint8_t);
361extern void io_apic_write(uint8_t, uint32_t);
362extern void io_apic_change_ioredtbl(uint8_t pin, uint8_t dest, uint8_t v, unsigned int);
363extern void io_apic_disable_irqs(uint16_t);
364extern void io_apic_enable_irqs(uint16_t);
[f761f1eb]365
366#endif
[b45c443]367
[06e1e95]368/** @}
[b45c443]369 */
Note: See TracBrowser for help on using the repository browser.