From patchwork Thu Sep 17 17:38:15 2015 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Shlomo Pongratz X-Patchwork-Id: 518985 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 97EE8141975 for ; Fri, 18 Sep 2015 03:37:59 +1000 (AEST) Authentication-Results: ozlabs.org; dkim=fail reason="signature verification failed" (2048-bit key; unprotected) header.d=gmail.com header.i=@gmail.com header.b=Ydyrptl8; dkim-atps=neutral Received: from localhost ([::1]:60294 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1Zcd89-0007zv-N9 for incoming@patchwork.ozlabs.org; Thu, 17 Sep 2015 13:37:57 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:39803) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1Zcd5j-0004FQ-7J for qemu-devel@nongnu.org; Thu, 17 Sep 2015 13:35:28 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1Zcd5h-00052g-Jq for qemu-devel@nongnu.org; Thu, 17 Sep 2015 13:35:26 -0400 Received: from mail-wi0-x22a.google.com ([2a00:1450:400c:c05::22a]:33591) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1Zcd5h-00052T-9I for qemu-devel@nongnu.org; Thu, 17 Sep 2015 13:35:25 -0400 Received: by wiclk2 with SMTP id lk2so33774502wic.0 for ; Thu, 17 Sep 2015 10:35:24 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=lYBrWgUndx1w/KpaWcaTYsRVjUd+MkEtkOYf4wDRUtM=; b=Ydyrptl8LbZ6kkbv4o0+ZryzlEpqCBHQAvRHg36rvKze53vli5WKtY7oCeh1ScJT0F LyoosrjZKUZppKD75d62iPjze3u2lg48z6nVb1vGnRdiqPiVYD0RXfyPSGC0qcjhCz/G n+X1JZA/r9P+8Zc3BfD7DcR/FTDV9xHhQ78lZ6pK1cG1GdTE3IVu+W44FJepREuwPrsi KSGZXehV6V4ZyiLmgJ55DUDi/FaCkRS5qmOOVw6uIIPoowuNf1zuU+iVxCz3DRQzh/O2 Zz+xfpylCEHH3E8yGJfezPhAtbf/vzyUzoz8H/UK1TBXzz7TixEWc+ETsKFKklZyQzUq u3Jg== X-Received: by 10.180.216.36 with SMTP id on4mr8654402wic.65.1442511324658; Thu, 17 Sep 2015 10:35:24 -0700 (PDT) Received: from localhost.localdomain (bzq-109-66-59-50.red.bezeqint.net. [109.66.59.50]) by smtp.gmail.com with ESMTPSA id ej5sm4512381wjd.22.2015.09.17.10.35.23 (version=TLSv1.2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Thu, 17 Sep 2015 10:35:24 -0700 (PDT) From: Shlomo Pongratz To: qemu-devel@nongnu.org Date: Thu, 17 Sep 2015 20:38:15 +0300 Message-Id: <1442511496-24050-4-git-send-email-shlomopongratz@gmail.com> X-Mailer: git-send-email 1.9.1 In-Reply-To: <1442511496-24050-1-git-send-email-shlomopongratz@gmail.com> References: <1442511496-24050-1-git-send-email-shlomopongratz@gmail.com> X-detected-operating-system: by eggs.gnu.org: Error: Malformed IPv6 address (bad octet value). X-Received-From: 2a00:1450:400c:c05::22a Cc: peter.maydell@linaro.org, eric.auger@linaro.org, Shlomo Pongratz , p.fedin@samsung.com, shannon.zhao@linaro.org, ashoks@broadcom.com, imammedo@redhat.com Subject: [Qemu-devel] [PATCH RFC V4 3/4] target-arm/cpu64 GICv3 system instructions support X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org From: Shlomo Pongratz Add system instructions used by the Linux (kernel) GICv3 device driver Signed-off-by: Shlomo Pongratz --- target-arm/cpu-qom.h | 1 + target-arm/cpu.h | 12 ++++++ target-arm/cpu64.c | 118 +++++++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 131 insertions(+) diff --git a/target-arm/cpu-qom.h b/target-arm/cpu-qom.h index 25fb1ce..d0bf602 100644 --- a/target-arm/cpu-qom.h +++ b/target-arm/cpu-qom.h @@ -220,6 +220,7 @@ hwaddr arm_cpu_get_phys_page_debug(CPUState *cpu, vaddr addr); int arm_cpu_gdb_read_register(CPUState *cpu, uint8_t *buf, int reg); int arm_cpu_gdb_write_register(CPUState *cpu, uint8_t *buf, int reg); +void aatch64_registers_with_opaque_set(Object *obj, void *opaque); /* Callback functions for the generic timer's timers. */ void arm_gt_ptimer_cb(void *opaque); diff --git a/target-arm/cpu.h b/target-arm/cpu.h index 1b80516..2ece8b9 100644 --- a/target-arm/cpu.h +++ b/target-arm/cpu.h @@ -1033,6 +1033,18 @@ void armv7m_nvic_set_pending(void *opaque, int irq); int armv7m_nvic_acknowledge_irq(void *opaque); void armv7m_nvic_complete_irq(void *opaque, int irq); +void armv8_gicv3_set_sgi(void *opaque, int cpuindex, uint64_t value); +uint64_t armv8_gicv3_acknowledge_irq(void *opaque, int cpuindex, + MemTxAttrs attrs); +void armv8_gicv3_complete_irq(void *opaque, int cpuindex, int irq, + MemTxAttrs attrs); +uint64_t armv8_gicv3_get_priority_mask(void *opaque, int cpuindex); +void armv8_gicv3_set_priority_mask(void *opaque, int cpuindex, uint32_t mask); +uint64_t armv8_gicv3_get_sre(void *opaque); +void armv8_gicv3_set_sre(void *opaque, uint64_t sre); +uint64_t armv8_gicv3_get_igrpen1(void *opaque, int cpuindex); +void armv8_gicv3_set_igrpen1(void *opaque, int cpuindex, uint64_t igrpen1); + /* Interface for defining coprocessor registers. * Registers are defined in tables of arm_cp_reginfo structs * which are passed to define_arm_cp_regs(). diff --git a/target-arm/cpu64.c b/target-arm/cpu64.c index 63c8b1c..4781f49 100644 --- a/target-arm/cpu64.c +++ b/target-arm/cpu64.c @@ -45,6 +45,115 @@ static uint64_t a57_a53_l2ctlr_read(CPUARMState *env, const ARMCPRegInfo *ri) } #endif +#ifndef CONFIG_USER_ONLY +static void sgi_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value) +{ + CPUState *cpu = ENV_GET_CPU(env); + armv8_gicv3_set_sgi(ri->opaque, cpu->cpu_index, value); +} + +static uint64_t iar_read(CPUARMState *env, const ARMCPRegInfo *ri) +{ + uint64_t value; + MemTxAttrs attrs;; + CPUState *cpu = ENV_GET_CPU(env); + attrs.secure = arm_is_secure_below_el3(env) ? 1 : 0; + value = armv8_gicv3_acknowledge_irq(ri->opaque, cpu->cpu_index, attrs); + return value; +} + +static void sre_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value) +{ + armv8_gicv3_set_sre(ri->opaque, value); +} + +static uint64_t sre_read(CPUARMState *env, const ARMCPRegInfo *ri) +{ + uint64_t value; + value = armv8_gicv3_get_sre(ri->opaque); + return value; +} + +static void eoir_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value) +{ + MemTxAttrs attrs; + CPUState *cpu = ENV_GET_CPU(env); + attrs.secure = arm_is_secure_below_el3(env) ? 1 : 0; + armv8_gicv3_complete_irq(ri->opaque, cpu->cpu_index, value, attrs); +} + +static uint64_t pmr_read(CPUARMState *env, const ARMCPRegInfo *ri) +{ + uint64_t value; + CPUState *cpu = ENV_GET_CPU(env); + value = armv8_gicv3_get_priority_mask(ri->opaque, cpu->cpu_index); + return value; +} + +static void pmr_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value) +{ + CPUState *cpu = ENV_GET_CPU(env); + armv8_gicv3_set_priority_mask(ri->opaque, cpu->cpu_index, value); +} + +static uint64_t igrpen1_read(CPUARMState *env, const ARMCPRegInfo *ri) +{ + uint64_t value; + CPUState *cpu = ENV_GET_CPU(env); + value = armv8_gicv3_get_igrpen1(ri->opaque, cpu->cpu_index); + return value; +} + +static void igrpen1_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value) +{ + CPUState *cpu = ENV_GET_CPU(env); + armv8_gicv3_set_igrpen1(ri->opaque, cpu->cpu_index, value); +} +#endif + +static const ARMCPRegInfo cortex_a57_a53_cp_with_opaque_reginfo[] = { + { .name = "EIOR1_EL1", .state = ARM_CP_STATE_AA64, +#ifndef CONFIG_USER_ONLY + .writefn = eoir_write, +#endif + .opc0 = 3, .opc1 = 0, .crn = 12, .crm = 12, .opc2 = 1, + .access = PL1_W, .type = ARM_CP_SPECIAL, .resetvalue = 0 }, + { .name = "IAR1_EL1", .state = ARM_CP_STATE_AA64, +#ifndef CONFIG_USER_ONLY + .readfn = iar_read, +#endif + .opc0 = 3, .opc1 = 0, .crn = 12, .crm = 12, .opc2 = 0, + .access = PL1_R, .type = ARM_CP_SPECIAL, .resetvalue = 0 }, + { .name = "SGI1R_EL1", .state = ARM_CP_STATE_AA64, +#ifndef CONFIG_USER_ONLY + .writefn = sgi_write, +#endif + .opc0 = 3, .opc1 = 0, .crn = 12, .crm = 11, .opc2 = 5, + .access = PL1_RW, .type = ARM_CP_SPECIAL, .resetvalue = 0 }, + { .name = "PMR_EL1", .state = ARM_CP_STATE_AA64, + .opc0 = 3, .opc1 = 0, .crn = 4, .crm = 6, .opc2 = 0, +#ifndef CONFIG_USER_ONLY + .readfn = pmr_read, .writefn = pmr_write, +#endif + .access = PL1_RW, .type = ARM_CP_SPECIAL, .resetvalue = 0 }, + { .name = "CTLR_EL1", .state = ARM_CP_STATE_AA64, + .opc0 = 3, .opc1 = 0, .crn = 12, .crm = 12, .opc2 = 4, + .access = PL1_RW, .type = ARM_CP_SPECIAL, .resetvalue = 0 }, + { .name = "SRE_EL1", .state = ARM_CP_STATE_AA64, + .opc0 = 3, .opc1 = 0, .crn = 12, .crm = 12, .opc2 = 5, .resetvalue = 0, +#ifndef CONFIG_USER_ONLY + .readfn = sre_read, .writefn = sre_write, +#endif + .access = PL1_RW, .type = ARM_CP_SPECIAL, .resetvalue = 0 }, + { .name = "IGRPEN1_EL1", .state = ARM_CP_STATE_AA64, + .opc0 = 3, .opc1 = 0, .crn = 12, .crm = 12, .opc2 = 7, +#ifndef CONFIG_USER_ONLY + .readfn = igrpen1_read, .writefn = igrpen1_write, +#endif + .access = PL1_RW, .type = ARM_CP_SPECIAL, .resetvalue = 0 }, + REGINFO_SENTINEL +}; + static const ARMCPRegInfo cortex_a57_a53_cp_reginfo[] = { #ifndef CONFIG_USER_ONLY { .name = "L2CTLR_EL1", .state = ARM_CP_STATE_AA64, @@ -258,6 +367,15 @@ static void aarch64_cpu_set_aarch64(Object *obj, bool value, Error **errp) } } +void aatch64_registers_with_opaque_set(Object *obj, void *opaque) +{ + ARMCPU *cpu = ARM_CPU(obj); + + define_arm_cp_regs_with_opaque(cpu, + cortex_a57_a53_cp_with_opaque_reginfo, + opaque); +} + static void aarch64_cpu_initfn(Object *obj) { object_property_add_bool(obj, "aarch64", aarch64_cpu_get_aarch64,