From nobody Fri Nov 7 04:08:02 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1546035861390155.16359093723952; Fri, 28 Dec 2018 14:24:21 -0800 (PST) Received: from localhost ([127.0.0.1]:33531 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1gd0YG-0001LK-0M for importer@patchew.org; Fri, 28 Dec 2018 17:24:20 -0500 Received: from eggs.gnu.org ([208.118.235.92]:48355) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1gd0Tw-00050Z-HG for qemu-devel@nongnu.org; Fri, 28 Dec 2018 17:19:56 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1gd0Kq-0000Gu-4i for qemu-devel@nongnu.org; Fri, 28 Dec 2018 17:10:31 -0500 Received: from mail-pf1-x444.google.com ([2607:f8b0:4864:20::444]:46150) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1gd0Ko-0008V7-6d for qemu-devel@nongnu.org; Fri, 28 Dec 2018 17:10:28 -0500 Received: by mail-pf1-x444.google.com with SMTP id c73so10937723pfe.13 for ; Fri, 28 Dec 2018 14:10:21 -0800 (PST) Received: from rohan.sifive.com ([12.206.222.5]) by smtp.gmail.com with ESMTPSA id a90sm76174790pfj.109.2018.12.28.14.10.20 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Fri, 28 Dec 2018 14:10:20 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=sifive.com; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=3/5EhJBB2z/MFvaUwgffAB+Y09T1pMm6MX8B2C4kGO0=; b=gRHHU7P1mRaoYVjO6Df2jk88DFc3zLBwV6nNg7MHM66WH7OeV2Q8PzrauwvBX2T5YJ IK4kfsP6xGUVOgE3/wjsoD//ff2Pts2zIfO6xN4ikuqHZZLYEDZGssZGmcGM48quFNlj mQgows/pr5Le/mTX1TcxXCieo1AWvmiqJvfus57jq5iLmFKkGZfaZvDlI09ZN0BiBm+p kfELqgbk7MGAlCe3e4dO2KKJzIn3s8HxwklGkp+IuBkBiTEwQlN6WBCEibU7TuKZk2ud kjsQ3u7lwtxVWsQS6ifBDzyyUXXs/tBjvVhTdNhTinVVWioD1eE2j9V+hsJCP/GfW3JL ZDZA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=3/5EhJBB2z/MFvaUwgffAB+Y09T1pMm6MX8B2C4kGO0=; b=p/KNRJOFny572ad+VT1oVj1WZLEgSYV8hJYajoMRwBM/hbZzNRxcVEJqQw67riUrlr kRRsucUGy9Q2r567OecroXuRskF5SZjObS5Guo73TKSPUp7pbB5eAzUYNCpLm2i8tUSy DuV1Yv8sTgUvgyLIn0tZr/IKWQTI+2ijhpsl/vDPLdMTjr3kHPSlIrBvUQ5FVvzjzImL on2vd0DEgyy+0dQPHM6ydhuHeYcb8cU2wbe+roF0fypjKaw5j7RvqW39vHdzEhdlWYuA TUz6SLj1RVHILtfAwrJ0G2ZJRyQyFNDbqFodfanylS3mgV7AcVqchRRnu1dMo5NcIALa TiBQ== X-Gm-Message-State: AJcUukdi3YM3Qk0OgWAxlHIY5pqlyDkVjcvj/z1xUC2nMHK7bnB6bL9y z/w/8e9DszxGNn49N2ovIPt0TqoZCs2bQg== X-Google-Smtp-Source: ALg8bN7+fAexkGEhDt90SN+15irOMpHJ9eTDTUzRxHXhjQdZ8TTUbceJBGRvtb5V6azB6Qf3xfTF7w== X-Received: by 2002:a63:ee0e:: with SMTP id e14mr27129157pgi.8.1546035020842; Fri, 28 Dec 2018 14:10:20 -0800 (PST) From: Jim Wilson To: qemu-devel@nongnu.org Date: Fri, 28 Dec 2018 14:10:18 -0800 Message-Id: <20181228221018.5022-1-jimw@sifive.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: References: X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2607:f8b0:4864:20::444 Subject: [Qemu-devel] [PATCH 4/5 v2] RISC-V: Add debug support for accessing CSRs. X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: qemu-riscv@nongnu.org, Jim Wilson Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Adds a debugger parameter to csr_read_helper and csr_write_helper. When this is true, we disable illegal instruction checks. Signed-off-by: Jim Wilson Reviewed-by: Alistair Francis Reviewed-by: Richard Henderson --- linux-user/riscv/signal.c | 5 ++- target/riscv/cpu.h | 7 +++- target/riscv/cpu_helper.c | 4 +- target/riscv/gdbstub.c | 4 +- target/riscv/op_helper.c | 93 ++++++++++++++++++++++++++++++++-----------= ---- 5 files changed, 76 insertions(+), 37 deletions(-) diff --git a/linux-user/riscv/signal.c b/linux-user/riscv/signal.c index f598d41..ed76f23 100644 --- a/linux-user/riscv/signal.c +++ b/linux-user/riscv/signal.c @@ -83,7 +83,8 @@ static void setup_sigcontext(struct target_sigcontext *sc= , CPURISCVState *env) __put_user(env->fpr[i], &sc->fpr[i]); } =20 - uint32_t fcsr =3D csr_read_helper(env, CSR_FCSR); /*riscv_get_fcsr(env= );*/ + /*riscv_get_fcsr(env);*/ + uint32_t fcsr =3D csr_read_helper(env, CSR_FCSR, false); __put_user(fcsr, &sc->fcsr); } =20 @@ -159,7 +160,7 @@ static void restore_sigcontext(CPURISCVState *env, stru= ct target_sigcontext *sc) =20 uint32_t fcsr; __get_user(fcsr, &sc->fcsr); - csr_write_helper(env, fcsr, CSR_FCSR); + csr_write_helper(env, fcsr, CSR_FCSR, false); } =20 static void restore_ucontext(CPURISCVState *env, struct target_ucontext *u= c) diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h index 4ee09b9..29361ca 100644 --- a/target/riscv/cpu.h +++ b/target/riscv/cpu.h @@ -290,8 +290,11 @@ static inline void cpu_get_tb_cpu_state(CPURISCVState = *env, target_ulong *pc, } =20 void csr_write_helper(CPURISCVState *env, target_ulong val_to_write, - target_ulong csrno); -target_ulong csr_read_helper(CPURISCVState *env, target_ulong csrno); + target_ulong csrno, bool debugger); +target_ulong csr_read_helper(CPURISCVState *env, target_ulong csrno, + bool debugger); + +void riscv_cpu_register_gdb_regs_for_features(CPUState *cs); =20 #include "exec/cpu-all.h" =20 diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c index 86f9f47..1abad94 100644 --- a/target/riscv/cpu_helper.c +++ b/target/riscv/cpu_helper.c @@ -526,7 +526,7 @@ void riscv_cpu_do_interrupt(CPUState *cs) get_field(s, MSTATUS_SIE) : get_field(s, MSTATUS_UIE << env->p= riv)); s =3D set_field(s, MSTATUS_SPP, env->priv); s =3D set_field(s, MSTATUS_SIE, 0); - csr_write_helper(env, s, CSR_MSTATUS); + csr_write_helper(env, s, CSR_MSTATUS, false); riscv_set_mode(env, PRV_S); } else { /* No need to check MTVEC for misaligned - lower 2 bits cannot be = set */ @@ -551,7 +551,7 @@ void riscv_cpu_do_interrupt(CPUState *cs) get_field(s, MSTATUS_MIE) : get_field(s, MSTATUS_UIE << env->p= riv)); s =3D set_field(s, MSTATUS_MPP, env->priv); s =3D set_field(s, MSTATUS_MIE, 0); - csr_write_helper(env, s, CSR_MSTATUS); + csr_write_helper(env, s, CSR_MSTATUS, false); riscv_set_mode(env, PRV_M); } /* TODO yield load reservation */ diff --git a/target/riscv/gdbstub.c b/target/riscv/gdbstub.c index 71c3eb1..b06f0fa 100644 --- a/target/riscv/gdbstub.c +++ b/target/riscv/gdbstub.c @@ -34,7 +34,7 @@ int riscv_cpu_gdb_read_register(CPUState *cs, uint8_t *me= m_buf, int n) } else if (n < 65) { return gdb_get_reg64(mem_buf, env->fpr[n - 33]); } else if (n < 4096 + 65) { - return gdb_get_regl(mem_buf, csr_read_helper(env, n - 65)); + return gdb_get_regl(mem_buf, csr_read_helper(env, n - 65, true)); } return 0; } @@ -57,7 +57,7 @@ int riscv_cpu_gdb_write_register(CPUState *cs, uint8_t *m= em_buf, int n) env->fpr[n - 33] =3D ldq_p(mem_buf); /* always 64-bit */ return sizeof(uint64_t); } else if (n < 4096 + 65) { - csr_write_helper(env, ldtul_p(mem_buf), n - 65); + csr_write_helper(env, ldtul_p(mem_buf), n - 65, true); } return 0; } diff --git a/target/riscv/op_helper.c b/target/riscv/op_helper.c index 3726299..3c5641e 100644 --- a/target/riscv/op_helper.c +++ b/target/riscv/op_helper.c @@ -87,7 +87,7 @@ static void validate_mstatus_fs(CPURISCVState *env, uintp= tr_t ra) * Adapted from Spike's processor_t::set_csr */ void csr_write_helper(CPURISCVState *env, target_ulong val_to_write, - target_ulong csrno) + target_ulong csrno, bool debugger) { #ifndef CONFIG_USER_ONLY uint64_t delegable_ints =3D MIP_SSIP | MIP_STIP | MIP_SEIP; @@ -96,15 +96,21 @@ void csr_write_helper(CPURISCVState *env, target_ulong = val_to_write, =20 switch (csrno) { case CSR_FFLAGS: - validate_mstatus_fs(env, GETPC()); + if (!debugger) { + validate_mstatus_fs(env, GETPC()); + } cpu_riscv_set_fflags(env, val_to_write & (FSR_AEXC >> FSR_AEXC_SHI= FT)); break; case CSR_FRM: - validate_mstatus_fs(env, GETPC()); + if (!debugger) { + validate_mstatus_fs(env, GETPC()); + } env->frm =3D val_to_write & (FSR_RD >> FSR_RD_SHIFT); break; case CSR_FCSR: - validate_mstatus_fs(env, GETPC()); + if (!debugger) { + validate_mstatus_fs(env, GETPC()); + } env->frm =3D (val_to_write & FSR_RD) >> FSR_RD_SHIFT; cpu_riscv_set_fflags(env, (val_to_write & FSR_AEXC) >> FSR_AEXC_SH= IFT); break; @@ -169,7 +175,9 @@ void csr_write_helper(CPURISCVState *env, target_ulong = val_to_write, * CLINT, no additional locking is needed for read-modifiy-write * CSR operations */ - qemu_mutex_lock_iothread(); + if (!debugger) { + qemu_mutex_lock_iothread(); + } RISCVCPU *cpu =3D riscv_env_get_cpu(env); riscv_cpu_update_mip(cpu, MIP_SSIP | MIP_STIP, (val_to_write & (MIP_SSIP | MIP_STIP))); @@ -177,7 +185,9 @@ void csr_write_helper(CPURISCVState *env, target_ulong = val_to_write, * csrs, csrc on mip.SEIP is not decomposable into separate read a= nd * write steps, so a different implementation is needed */ - qemu_mutex_unlock_iothread(); + if (!debugger) { + qemu_mutex_unlock_iothread(); + } break; } case CSR_MIE: { @@ -247,21 +257,25 @@ void csr_write_helper(CPURISCVState *env, target_ulon= g val_to_write, mask |=3D SSTATUS_MXR; } ms =3D (ms & ~mask) | (val_to_write & mask); - csr_write_helper(env, ms, CSR_MSTATUS); + csr_write_helper(env, ms, CSR_MSTATUS, debugger); break; } case CSR_SIP: { - qemu_mutex_lock_iothread(); + if (!debugger) { + qemu_mutex_lock_iothread(); + } target_ulong next_mip =3D (env->mip & ~env->mideleg) | (val_to_write & env->mideleg); - qemu_mutex_unlock_iothread(); - csr_write_helper(env, next_mip, CSR_MIP); + if (!debugger) { + qemu_mutex_unlock_iothread(); + } + csr_write_helper(env, next_mip, CSR_MIP, debugger); break; } case CSR_SIE: { target_ulong next_mie =3D (env->mie & ~env->mideleg) | (val_to_write & env->mideleg); - csr_write_helper(env, next_mie, CSR_MIE); + csr_write_helper(env, next_mie, CSR_MIE, debugger); break; } case CSR_SATP: /* CSR_SPTBR */ { @@ -371,7 +385,9 @@ void csr_write_helper(CPURISCVState *env, target_ulong = val_to_write, do_illegal: #endif default: - do_raise_exception_err(env, RISCV_EXCP_ILLEGAL_INST, GETPC()); + if (!debugger) { + do_raise_exception_err(env, RISCV_EXCP_ILLEGAL_INST, GETPC()); + } } } =20 @@ -380,7 +396,8 @@ void csr_write_helper(CPURISCVState *env, target_ulong = val_to_write, * * Adapted from Spike's processor_t::get_csr */ -target_ulong csr_read_helper(CPURISCVState *env, target_ulong csrno) +target_ulong csr_read_helper(CPURISCVState *env, target_ulong csrno, + bool debugger) { #ifndef CONFIG_USER_ONLY target_ulong ctr_en =3D env->priv =3D=3D PRV_U ? env->scounteren : @@ -416,13 +433,19 @@ target_ulong csr_read_helper(CPURISCVState *env, targ= et_ulong csrno) =20 switch (csrno) { case CSR_FFLAGS: - validate_mstatus_fs(env, GETPC()); + if (!debugger) { + validate_mstatus_fs(env, GETPC()); + } return cpu_riscv_get_fflags(env); case CSR_FRM: - validate_mstatus_fs(env, GETPC()); + if (!debugger) { + validate_mstatus_fs(env, GETPC()); + } return env->frm; case CSR_FCSR: - validate_mstatus_fs(env, GETPC()); + if (!debugger) { + validate_mstatus_fs(env, GETPC()); + } return (cpu_riscv_get_fflags(env) << FSR_AEXC_SHIFT) | (env->frm << FSR_RD_SHIFT); /* rdtime/rdtimeh is trapped and emulated by bbl in system mode */ @@ -504,9 +527,13 @@ target_ulong csr_read_helper(CPURISCVState *env, targe= t_ulong csrno) return env->mstatus & mask; } case CSR_SIP: { - qemu_mutex_lock_iothread(); + if (!debugger) { + qemu_mutex_lock_iothread(); + } target_ulong tmp =3D env->mip & env->mideleg; - qemu_mutex_unlock_iothread(); + if (!debugger) { + qemu_mutex_unlock_iothread(); + } return tmp; } case CSR_SIE: @@ -539,9 +566,13 @@ target_ulong csr_read_helper(CPURISCVState *env, targe= t_ulong csrno) case CSR_MSTATUS: return env->mstatus; case CSR_MIP: { - qemu_mutex_lock_iothread(); + if (!debugger) { + qemu_mutex_lock_iothread(); + } target_ulong tmp =3D env->mip; - qemu_mutex_unlock_iothread(); + if (!debugger) { + qemu_mutex_unlock_iothread(); + } return tmp; } case CSR_MIE: @@ -601,7 +632,11 @@ target_ulong csr_read_helper(CPURISCVState *env, targe= t_ulong csrno) #endif } /* used by e.g. MTIME read */ - do_raise_exception_err(env, RISCV_EXCP_ILLEGAL_INST, GETPC()); + if (!debugger) { + do_raise_exception_err(env, RISCV_EXCP_ILLEGAL_INST, GETPC()); + } else { + return 0; + } } =20 /* @@ -625,8 +660,8 @@ target_ulong helper_csrrw(CPURISCVState *env, target_ul= ong src, target_ulong csr) { validate_csr(env, csr, 1, GETPC()); - uint64_t csr_backup =3D csr_read_helper(env, csr); - csr_write_helper(env, src, csr); + uint64_t csr_backup =3D csr_read_helper(env, csr, false); + csr_write_helper(env, src, csr, false); return csr_backup; } =20 @@ -634,9 +669,9 @@ target_ulong helper_csrrs(CPURISCVState *env, target_ul= ong src, target_ulong csr, target_ulong rs1_pass) { validate_csr(env, csr, rs1_pass !=3D 0, GETPC()); - uint64_t csr_backup =3D csr_read_helper(env, csr); + uint64_t csr_backup =3D csr_read_helper(env, csr, false); if (rs1_pass !=3D 0) { - csr_write_helper(env, src | csr_backup, csr); + csr_write_helper(env, src | csr_backup, csr, false); } return csr_backup; } @@ -645,9 +680,9 @@ target_ulong helper_csrrc(CPURISCVState *env, target_ul= ong src, target_ulong csr, target_ulong rs1_pass) { validate_csr(env, csr, rs1_pass !=3D 0, GETPC()); - uint64_t csr_backup =3D csr_read_helper(env, csr); + uint64_t csr_backup =3D csr_read_helper(env, csr, false); if (rs1_pass !=3D 0) { - csr_write_helper(env, (~src) & csr_backup, csr); + csr_write_helper(env, (~src) & csr_backup, csr, false); } return csr_backup; } @@ -674,7 +709,7 @@ target_ulong helper_sret(CPURISCVState *env, target_ulo= ng cpu_pc_deb) mstatus =3D set_field(mstatus, MSTATUS_SPIE, 0); mstatus =3D set_field(mstatus, MSTATUS_SPP, PRV_U); riscv_set_mode(env, prev_priv); - csr_write_helper(env, mstatus, CSR_MSTATUS); + csr_write_helper(env, mstatus, CSR_MSTATUS, false); =20 return retpc; } @@ -699,7 +734,7 @@ target_ulong helper_mret(CPURISCVState *env, target_ulo= ng cpu_pc_deb) mstatus =3D set_field(mstatus, MSTATUS_MPIE, 0); mstatus =3D set_field(mstatus, MSTATUS_MPP, PRV_U); riscv_set_mode(env, prev_priv); - csr_write_helper(env, mstatus, CSR_MSTATUS); + csr_write_helper(env, mstatus, CSR_MSTATUS, false); =20 return retpc; } --=20 2.7.4