@@ -20,6 +20,7 @@
*/
#include <libcflat.h>
#include <asm/gic.h>
+#include <asm/gic-v3-its.h>
#define NTIMES (1U << 16)
@@ -156,6 +157,48 @@ static void ipi_exec(void)
assert_msg(irq_received, "failed to receive IPI in time, but received %d successfully\n", nr_ipi_received);
}
+static bool lpi_prep(void)
+{
+ struct its_collection *col1;
+ struct its_device *dev2;
+
+ if (!gicv3_its_base())
+ return false;
+
+ its_enable_defaults();
+ dev2 = its_create_device(2 /* dev id */, 8 /* nb_ites */);
+ col1 = its_create_collection(1 /* col id */, 1 /* target PE */);
+ gicv3_lpi_set_config(8199, LPI_PROP_DEFAULT);
+
+ its_send_mapd_nv(dev2, true);
+ its_send_mapc_nv(col1, true);
+ its_send_invall_nv(col1);
+ its_send_mapti_nv(dev2, 8199 /* lpi id */, 20 /* event id */, col1);
+
+ gic_prep_common();
+ return true;
+}
+
+static void lpi_exec(void)
+{
+ struct its_device *dev2;
+ unsigned tries = 1 << 28;
+ static int received = 0;
+
+ irq_received = false;
+
+ dev2 = its_get_device(2);
+ its_send_int_nv(dev2, 20);
+
+ while (!irq_received && tries--)
+ cpu_relax();
+
+ if (irq_received)
+ ++received;
+
+ assert_msg(irq_received, "failed to receive LPI in time, but received %d successfully\n", received);
+}
+
static void hvc_exec(void)
{
asm volatile("mov w0, #0x4b000000; hvc #0" ::: "w0");
@@ -201,6 +244,7 @@ static struct exit_test tests[] = {
{"eoi", NULL, eoi_exec, true},
{"ipi", ipi_prep, ipi_exec, true},
{"ipi_hw", ipi_hw_prep, ipi_exec, true},
+ {"lpi", lpi_prep, lpi_exec, true},
};
struct ns_time {