2 * QEMU PowerPC pSeries Logical Partition (aka sPAPR) hardware System Emulator
4 * PAPR Virtualized Interrupt System, aka ICS/ICP aka xics
6 * Copyright (c) 2010,2011 David Gibson, IBM Corporation.
8 * Permission is hereby granted, free of charge, to any person obtaining a copy
9 * of this software and associated documentation files (the "Software"), to deal
10 * in the Software without restriction, including without limitation the rights
11 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
12 * copies of the Software, and to permit persons to whom the Software is
13 * furnished to do so, subject to the following conditions:
15 * The above copyright notice and this permission notice shall be included in
16 * all copies or substantial portions of the Software.
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
21 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
28 #include "qemu/osdep.h"
29 #include "qapi/error.h"
30 #include "qemu-common.h"
34 #include "qemu/timer.h"
35 #include "hw/ppc/xics.h"
36 #include "qemu/error-report.h"
37 #include "qapi/visitor.h"
38 #include "monitor/monitor.h"
39 #include "hw/intc/intc.h"
40 #include "sysemu/kvm.h"
42 void icp_pic_print_info(ICPState
*icp
, Monitor
*mon
)
44 int cpu_index
= icp
->cs
? icp
->cs
->cpu_index
: -1;
50 if (kvm_irqchip_in_kernel()) {
51 icp_synchronize_state(icp
);
54 monitor_printf(mon
, "CPU %d XIRR=%08x (%p) PP=%02x MFRR=%02x\n",
55 cpu_index
, icp
->xirr
, icp
->xirr_owner
,
56 icp
->pending_priority
, icp
->mfrr
);
59 void ics_pic_print_info(ICSState
*ics
, Monitor
*mon
)
63 monitor_printf(mon
, "ICS %4x..%4x %p\n",
64 ics
->offset
, ics
->offset
+ ics
->nr_irqs
- 1, ics
);
70 if (kvm_irqchip_in_kernel()) {
71 ics_synchronize_state(ics
);
74 for (i
= 0; i
< ics
->nr_irqs
; i
++) {
75 ICSIRQState
*irq
= ics
->irqs
+ i
;
77 if (!(irq
->flags
& XICS_FLAGS_IRQ_MASK
)) {
80 monitor_printf(mon
, " %4x %s %02x %02x\n",
82 (irq
->flags
& XICS_FLAGS_IRQ_LSI
) ?
84 irq
->priority
, irq
->status
);
89 * ICP: Presentation layer
92 #define XISR_MASK 0x00ffffff
93 #define CPPR_MASK 0xff000000
95 #define XISR(icp) (((icp)->xirr) & XISR_MASK)
96 #define CPPR(icp) (((icp)->xirr) >> 24)
98 static void ics_reject(ICSState
*ics
, uint32_t nr
)
100 ICSStateClass
*k
= ICS_BASE_GET_CLASS(ics
);
107 void ics_resend(ICSState
*ics
)
109 ICSStateClass
*k
= ICS_BASE_GET_CLASS(ics
);
116 static void ics_eoi(ICSState
*ics
, int nr
)
118 ICSStateClass
*k
= ICS_BASE_GET_CLASS(ics
);
125 static void icp_check_ipi(ICPState
*icp
)
127 if (XISR(icp
) && (icp
->pending_priority
<= icp
->mfrr
)) {
131 trace_xics_icp_check_ipi(icp
->cs
->cpu_index
, icp
->mfrr
);
133 if (XISR(icp
) && icp
->xirr_owner
) {
134 ics_reject(icp
->xirr_owner
, XISR(icp
));
137 icp
->xirr
= (icp
->xirr
& ~XISR_MASK
) | XICS_IPI
;
138 icp
->pending_priority
= icp
->mfrr
;
139 icp
->xirr_owner
= NULL
;
140 qemu_irq_raise(icp
->output
);
143 void icp_resend(ICPState
*icp
)
145 XICSFabric
*xi
= icp
->xics
;
146 XICSFabricClass
*xic
= XICS_FABRIC_GET_CLASS(xi
);
148 if (icp
->mfrr
< CPPR(icp
)) {
155 void icp_set_cppr(ICPState
*icp
, uint8_t cppr
)
160 old_cppr
= CPPR(icp
);
161 icp
->xirr
= (icp
->xirr
& ~CPPR_MASK
) | (cppr
<< 24);
163 if (cppr
< old_cppr
) {
164 if (XISR(icp
) && (cppr
<= icp
->pending_priority
)) {
165 old_xisr
= XISR(icp
);
166 icp
->xirr
&= ~XISR_MASK
; /* Clear XISR */
167 icp
->pending_priority
= 0xff;
168 qemu_irq_lower(icp
->output
);
169 if (icp
->xirr_owner
) {
170 ics_reject(icp
->xirr_owner
, old_xisr
);
171 icp
->xirr_owner
= NULL
;
181 void icp_set_mfrr(ICPState
*icp
, uint8_t mfrr
)
184 if (mfrr
< CPPR(icp
)) {
189 uint32_t icp_accept(ICPState
*icp
)
191 uint32_t xirr
= icp
->xirr
;
193 qemu_irq_lower(icp
->output
);
194 icp
->xirr
= icp
->pending_priority
<< 24;
195 icp
->pending_priority
= 0xff;
196 icp
->xirr_owner
= NULL
;
198 trace_xics_icp_accept(xirr
, icp
->xirr
);
203 uint32_t icp_ipoll(ICPState
*icp
, uint32_t *mfrr
)
211 void icp_eoi(ICPState
*icp
, uint32_t xirr
)
213 XICSFabric
*xi
= icp
->xics
;
214 XICSFabricClass
*xic
= XICS_FABRIC_GET_CLASS(xi
);
218 /* Send EOI -> ICS */
219 icp
->xirr
= (icp
->xirr
& ~CPPR_MASK
) | (xirr
& CPPR_MASK
);
220 trace_xics_icp_eoi(icp
->cs
->cpu_index
, xirr
, icp
->xirr
);
221 irq
= xirr
& XISR_MASK
;
223 ics
= xic
->ics_get(xi
, irq
);
232 static void icp_irq(ICSState
*ics
, int server
, int nr
, uint8_t priority
)
234 ICPState
*icp
= xics_icp_get(ics
->xics
, server
);
236 trace_xics_icp_irq(server
, nr
, priority
);
238 if ((priority
>= CPPR(icp
))
239 || (XISR(icp
) && (icp
->pending_priority
<= priority
))) {
242 if (XISR(icp
) && icp
->xirr_owner
) {
243 ics_reject(icp
->xirr_owner
, XISR(icp
));
244 icp
->xirr_owner
= NULL
;
246 icp
->xirr
= (icp
->xirr
& ~XISR_MASK
) | (nr
& XISR_MASK
);
247 icp
->xirr_owner
= ics
;
248 icp
->pending_priority
= priority
;
249 trace_xics_icp_raise(icp
->xirr
, icp
->pending_priority
);
250 qemu_irq_raise(icp
->output
);
254 static int icp_pre_save(void *opaque
)
256 ICPState
*icp
= opaque
;
258 if (kvm_irqchip_in_kernel()) {
259 icp_get_kvm_state(icp
);
265 static int icp_post_load(void *opaque
, int version_id
)
267 ICPState
*icp
= opaque
;
269 if (kvm_irqchip_in_kernel()) {
270 return icp_set_kvm_state(icp
);
276 static const VMStateDescription vmstate_icp_server
= {
277 .name
= "icp/server",
279 .minimum_version_id
= 1,
280 .pre_save
= icp_pre_save
,
281 .post_load
= icp_post_load
,
282 .fields
= (VMStateField
[]) {
284 VMSTATE_UINT32(xirr
, ICPState
),
285 VMSTATE_UINT8(pending_priority
, ICPState
),
286 VMSTATE_UINT8(mfrr
, ICPState
),
287 VMSTATE_END_OF_LIST()
291 static void icp_reset_handler(void *dev
)
293 ICPState
*icp
= ICP(dev
);
296 icp
->pending_priority
= 0xff;
299 /* Make all outputs are deasserted */
300 qemu_set_irq(icp
->output
, 0);
302 if (kvm_irqchip_in_kernel()) {
303 icp_set_kvm_state(ICP(dev
));
307 static void icp_realize(DeviceState
*dev
, Error
**errp
)
309 ICPState
*icp
= ICP(dev
);
315 obj
= object_property_get_link(OBJECT(dev
), ICP_PROP_XICS
, &err
);
317 error_propagate_prepend(errp
, err
,
318 "required link '" ICP_PROP_XICS
323 icp
->xics
= XICS_FABRIC(obj
);
325 obj
= object_property_get_link(OBJECT(dev
), ICP_PROP_CPU
, &err
);
327 error_propagate_prepend(errp
, err
,
328 "required link '" ICP_PROP_CPU
333 cpu
= POWERPC_CPU(obj
);
337 switch (PPC_INPUT(env
)) {
338 case PPC_FLAGS_INPUT_POWER7
:
339 icp
->output
= env
->irq_inputs
[POWER7_INPUT_INT
];
341 case PPC_FLAGS_INPUT_POWER9
: /* For SPAPR xics emulation */
342 icp
->output
= env
->irq_inputs
[POWER9_INPUT_INT
];
345 case PPC_FLAGS_INPUT_970
:
346 icp
->output
= env
->irq_inputs
[PPC970_INPUT_INT
];
350 error_setg(errp
, "XICS interrupt controller does not support this CPU bus model");
354 if (kvm_irqchip_in_kernel()) {
355 icp_kvm_realize(dev
, &err
);
357 error_propagate(errp
, err
);
362 qemu_register_reset(icp_reset_handler
, dev
);
363 vmstate_register(NULL
, icp
->cs
->cpu_index
, &vmstate_icp_server
, icp
);
366 static void icp_unrealize(DeviceState
*dev
, Error
**errp
)
368 ICPState
*icp
= ICP(dev
);
370 vmstate_unregister(NULL
, &vmstate_icp_server
, icp
);
371 qemu_unregister_reset(icp_reset_handler
, dev
);
374 static void icp_class_init(ObjectClass
*klass
, void *data
)
376 DeviceClass
*dc
= DEVICE_CLASS(klass
);
378 dc
->realize
= icp_realize
;
379 dc
->unrealize
= icp_unrealize
;
382 static const TypeInfo icp_info
= {
384 .parent
= TYPE_DEVICE
,
385 .instance_size
= sizeof(ICPState
),
386 .class_init
= icp_class_init
,
387 .class_size
= sizeof(ICPStateClass
),
390 Object
*icp_create(Object
*cpu
, const char *type
, XICSFabric
*xi
, Error
**errp
)
392 Error
*local_err
= NULL
;
395 obj
= object_new(type
);
396 object_property_add_child(cpu
, type
, obj
, &error_abort
);
398 object_property_add_const_link(obj
, ICP_PROP_XICS
, OBJECT(xi
),
400 object_property_add_const_link(obj
, ICP_PROP_CPU
, cpu
, &error_abort
);
401 object_property_set_bool(obj
, true, "realized", &local_err
);
403 object_unparent(obj
);
404 error_propagate(errp
, local_err
);
414 static void ics_simple_resend_msi(ICSState
*ics
, int srcno
)
416 ICSIRQState
*irq
= ics
->irqs
+ srcno
;
418 /* FIXME: filter by server#? */
419 if (irq
->status
& XICS_STATUS_REJECTED
) {
420 irq
->status
&= ~XICS_STATUS_REJECTED
;
421 if (irq
->priority
!= 0xff) {
422 icp_irq(ics
, irq
->server
, srcno
+ ics
->offset
, irq
->priority
);
427 static void ics_simple_resend_lsi(ICSState
*ics
, int srcno
)
429 ICSIRQState
*irq
= ics
->irqs
+ srcno
;
431 if ((irq
->priority
!= 0xff)
432 && (irq
->status
& XICS_STATUS_ASSERTED
)
433 && !(irq
->status
& XICS_STATUS_SENT
)) {
434 irq
->status
|= XICS_STATUS_SENT
;
435 icp_irq(ics
, irq
->server
, srcno
+ ics
->offset
, irq
->priority
);
439 static void ics_simple_set_irq_msi(ICSState
*ics
, int srcno
, int val
)
441 ICSIRQState
*irq
= ics
->irqs
+ srcno
;
443 trace_xics_ics_simple_set_irq_msi(srcno
, srcno
+ ics
->offset
);
446 if (irq
->priority
== 0xff) {
447 irq
->status
|= XICS_STATUS_MASKED_PENDING
;
448 trace_xics_masked_pending();
450 icp_irq(ics
, irq
->server
, srcno
+ ics
->offset
, irq
->priority
);
455 static void ics_simple_set_irq_lsi(ICSState
*ics
, int srcno
, int val
)
457 ICSIRQState
*irq
= ics
->irqs
+ srcno
;
459 trace_xics_ics_simple_set_irq_lsi(srcno
, srcno
+ ics
->offset
);
461 irq
->status
|= XICS_STATUS_ASSERTED
;
463 irq
->status
&= ~XICS_STATUS_ASSERTED
;
465 ics_simple_resend_lsi(ics
, srcno
);
468 void ics_simple_set_irq(void *opaque
, int srcno
, int val
)
470 ICSState
*ics
= (ICSState
*)opaque
;
472 if (kvm_irqchip_in_kernel()) {
473 ics_kvm_set_irq(ics
, srcno
, val
);
477 if (ics
->irqs
[srcno
].flags
& XICS_FLAGS_IRQ_LSI
) {
478 ics_simple_set_irq_lsi(ics
, srcno
, val
);
480 ics_simple_set_irq_msi(ics
, srcno
, val
);
484 static void ics_simple_write_xive_msi(ICSState
*ics
, int srcno
)
486 ICSIRQState
*irq
= ics
->irqs
+ srcno
;
488 if (!(irq
->status
& XICS_STATUS_MASKED_PENDING
)
489 || (irq
->priority
== 0xff)) {
493 irq
->status
&= ~XICS_STATUS_MASKED_PENDING
;
494 icp_irq(ics
, irq
->server
, srcno
+ ics
->offset
, irq
->priority
);
497 static void ics_simple_write_xive_lsi(ICSState
*ics
, int srcno
)
499 ics_simple_resend_lsi(ics
, srcno
);
502 void ics_simple_write_xive(ICSState
*ics
, int srcno
, int server
,
503 uint8_t priority
, uint8_t saved_priority
)
505 ICSIRQState
*irq
= ics
->irqs
+ srcno
;
507 irq
->server
= server
;
508 irq
->priority
= priority
;
509 irq
->saved_priority
= saved_priority
;
511 trace_xics_ics_simple_write_xive(ics
->offset
+ srcno
, srcno
, server
,
514 if (ics
->irqs
[srcno
].flags
& XICS_FLAGS_IRQ_LSI
) {
515 ics_simple_write_xive_lsi(ics
, srcno
);
517 ics_simple_write_xive_msi(ics
, srcno
);
521 static void ics_simple_reject(ICSState
*ics
, uint32_t nr
)
523 ICSIRQState
*irq
= ics
->irqs
+ nr
- ics
->offset
;
525 trace_xics_ics_simple_reject(nr
, nr
- ics
->offset
);
526 if (irq
->flags
& XICS_FLAGS_IRQ_MSI
) {
527 irq
->status
|= XICS_STATUS_REJECTED
;
528 } else if (irq
->flags
& XICS_FLAGS_IRQ_LSI
) {
529 irq
->status
&= ~XICS_STATUS_SENT
;
533 static void ics_simple_resend(ICSState
*ics
)
537 for (i
= 0; i
< ics
->nr_irqs
; i
++) {
538 /* FIXME: filter by server#? */
539 if (ics
->irqs
[i
].flags
& XICS_FLAGS_IRQ_LSI
) {
540 ics_simple_resend_lsi(ics
, i
);
542 ics_simple_resend_msi(ics
, i
);
547 static void ics_simple_eoi(ICSState
*ics
, uint32_t nr
)
549 int srcno
= nr
- ics
->offset
;
550 ICSIRQState
*irq
= ics
->irqs
+ srcno
;
552 trace_xics_ics_simple_eoi(nr
);
554 if (ics
->irqs
[srcno
].flags
& XICS_FLAGS_IRQ_LSI
) {
555 irq
->status
&= ~XICS_STATUS_SENT
;
559 static void ics_simple_reset(DeviceState
*dev
)
561 ICSStateClass
*icsc
= ICS_BASE_GET_CLASS(dev
);
563 icsc
->parent_reset(dev
);
565 if (kvm_irqchip_in_kernel()) {
566 ics_set_kvm_state(ICS_BASE(dev
));
570 static void ics_simple_reset_handler(void *dev
)
572 ics_simple_reset(dev
);
575 static void ics_simple_realize(DeviceState
*dev
, Error
**errp
)
577 ICSState
*ics
= ICS_SIMPLE(dev
);
578 ICSStateClass
*icsc
= ICS_BASE_GET_CLASS(ics
);
579 Error
*local_err
= NULL
;
581 icsc
->parent_realize(dev
, &local_err
);
583 error_propagate(errp
, local_err
);
587 qemu_register_reset(ics_simple_reset_handler
, ics
);
590 static void ics_simple_class_init(ObjectClass
*klass
, void *data
)
592 DeviceClass
*dc
= DEVICE_CLASS(klass
);
593 ICSStateClass
*isc
= ICS_BASE_CLASS(klass
);
595 device_class_set_parent_realize(dc
, ics_simple_realize
,
596 &isc
->parent_realize
);
597 device_class_set_parent_reset(dc
, ics_simple_reset
,
600 isc
->reject
= ics_simple_reject
;
601 isc
->resend
= ics_simple_resend
;
602 isc
->eoi
= ics_simple_eoi
;
605 static const TypeInfo ics_simple_info
= {
606 .name
= TYPE_ICS_SIMPLE
,
607 .parent
= TYPE_ICS_BASE
,
608 .instance_size
= sizeof(ICSState
),
609 .class_init
= ics_simple_class_init
,
610 .class_size
= sizeof(ICSStateClass
),
613 static void ics_base_reset(DeviceState
*dev
)
615 ICSState
*ics
= ICS_BASE(dev
);
617 uint8_t flags
[ics
->nr_irqs
];
619 for (i
= 0; i
< ics
->nr_irqs
; i
++) {
620 flags
[i
] = ics
->irqs
[i
].flags
;
623 memset(ics
->irqs
, 0, sizeof(ICSIRQState
) * ics
->nr_irqs
);
625 for (i
= 0; i
< ics
->nr_irqs
; i
++) {
626 ics
->irqs
[i
].priority
= 0xff;
627 ics
->irqs
[i
].saved_priority
= 0xff;
628 ics
->irqs
[i
].flags
= flags
[i
];
632 static void ics_base_realize(DeviceState
*dev
, Error
**errp
)
634 ICSState
*ics
= ICS_BASE(dev
);
638 obj
= object_property_get_link(OBJECT(dev
), ICS_PROP_XICS
, &err
);
640 error_propagate_prepend(errp
, err
,
641 "required link '" ICS_PROP_XICS
645 ics
->xics
= XICS_FABRIC(obj
);
648 error_setg(errp
, "Number of interrupts needs to be greater 0");
651 ics
->irqs
= g_malloc0(ics
->nr_irqs
* sizeof(ICSIRQState
));
654 static void ics_base_instance_init(Object
*obj
)
656 ICSState
*ics
= ICS_BASE(obj
);
658 ics
->offset
= XICS_IRQ_BASE
;
661 static int ics_base_pre_save(void *opaque
)
663 ICSState
*ics
= opaque
;
665 if (kvm_irqchip_in_kernel()) {
666 ics_get_kvm_state(ics
);
672 static int ics_base_post_load(void *opaque
, int version_id
)
674 ICSState
*ics
= opaque
;
676 if (kvm_irqchip_in_kernel()) {
677 return ics_set_kvm_state(ics
);
683 static const VMStateDescription vmstate_ics_base_irq
= {
686 .minimum_version_id
= 1,
687 .fields
= (VMStateField
[]) {
688 VMSTATE_UINT32(server
, ICSIRQState
),
689 VMSTATE_UINT8(priority
, ICSIRQState
),
690 VMSTATE_UINT8(saved_priority
, ICSIRQState
),
691 VMSTATE_UINT8(status
, ICSIRQState
),
692 VMSTATE_UINT8(flags
, ICSIRQState
),
693 VMSTATE_END_OF_LIST()
697 static const VMStateDescription vmstate_ics_base
= {
700 .minimum_version_id
= 1,
701 .pre_save
= ics_base_pre_save
,
702 .post_load
= ics_base_post_load
,
703 .fields
= (VMStateField
[]) {
705 VMSTATE_UINT32_EQUAL(nr_irqs
, ICSState
, NULL
),
707 VMSTATE_STRUCT_VARRAY_POINTER_UINT32(irqs
, ICSState
, nr_irqs
,
708 vmstate_ics_base_irq
,
710 VMSTATE_END_OF_LIST()
714 static Property ics_base_properties
[] = {
715 DEFINE_PROP_UINT32("nr-irqs", ICSState
, nr_irqs
, 0),
716 DEFINE_PROP_END_OF_LIST(),
719 static void ics_base_class_init(ObjectClass
*klass
, void *data
)
721 DeviceClass
*dc
= DEVICE_CLASS(klass
);
723 dc
->realize
= ics_base_realize
;
724 dc
->props
= ics_base_properties
;
725 dc
->reset
= ics_base_reset
;
726 dc
->vmsd
= &vmstate_ics_base
;
729 static const TypeInfo ics_base_info
= {
730 .name
= TYPE_ICS_BASE
,
731 .parent
= TYPE_DEVICE
,
733 .instance_size
= sizeof(ICSState
),
734 .instance_init
= ics_base_instance_init
,
735 .class_init
= ics_base_class_init
,
736 .class_size
= sizeof(ICSStateClass
),
739 static const TypeInfo xics_fabric_info
= {
740 .name
= TYPE_XICS_FABRIC
,
741 .parent
= TYPE_INTERFACE
,
742 .class_size
= sizeof(XICSFabricClass
),
748 ICPState
*xics_icp_get(XICSFabric
*xi
, int server
)
750 XICSFabricClass
*xic
= XICS_FABRIC_GET_CLASS(xi
);
752 return xic
->icp_get(xi
, server
);
755 void ics_set_irq_type(ICSState
*ics
, int srcno
, bool lsi
)
757 assert(!(ics
->irqs
[srcno
].flags
& XICS_FLAGS_IRQ_MASK
));
759 ics
->irqs
[srcno
].flags
|=
760 lsi
? XICS_FLAGS_IRQ_LSI
: XICS_FLAGS_IRQ_MSI
;
762 if (kvm_irqchip_in_kernel()) {
763 ics_set_kvm_state_one(ics
, srcno
);
767 static void xics_register_types(void)
769 type_register_static(&ics_simple_info
);
770 type_register_static(&ics_base_info
);
771 type_register_static(&icp_info
);
772 type_register_static(&xics_fabric_info
);
775 type_init(xics_register_types
)