[PATCH v2 3/3] RISC-V: Support new CSR macro DECLARE_CSR_REUSE to handle the reused CSR.

Nelson Chu nelson.chu@sifive.com
Tue Jun 30 02:55:16 GMT 2020


Hi Jim,

On Tue, Jun 30, 2020 at 7:52 AM Jim Wilson <jimw@sifive.com> wrote:
> On Wed, Jun 24, 2020 at 8:38 PM Nelson Chu <nelson.chu@sifive.com> wrote:
> > gdb only handles the CSR which are defined by DECLARE_CSR, and the aliases CSR
> > which are defined by DECLARE_CSR_ALIAS.  Supporting the reused CSR in gdb is not
> > good enough and may cause problems so far, so just skip the DECLARE_CSR_REUSE.
>
> I think this breaks gdb/qemu interaction.  qemu will send an xml file
> that mentions mucounteren, and gdb will error because it doesn't know
> what the mucounteren register is anymore.  You have to update gdb to
> handle DECLARE_CSR_REUSE same as DECLARE_CSR_ALIAS.  Once they are
> handled the same, it isn't clear why we need both of them, unless you
> plan to handle them differently in the future.

I notice the current gdb just creates aliases if their aborted version
is newer than v1.11.  Therefore, the following CSR are unknown for gdb
if qemu send an xml file that mentions them,

* privileged CSR
ubadaddr, sbadaddr, sptbr, mbadaddr, mucounteren
* unprivileged debug CSR
dscratch, mcontrol, icount, itrigger, etrigger, textra32, textra64

* gdb/riscv-tdep.c
static void
riscv_create_csr_aliases ()
{
  for (auto &reg : riscv_csr_feature.registers)
    {
      int csr_num = reg.regnum - RISCV_FIRST_CSR_REGNUM;
      const char *alias = xstrprintf ("csr%d", csr_num);
      reg.names.push_back (alias);

      /* Setup the other csr aliases.  We don't use a switch table here in
         case there are multiple aliases with the same value.  Also filter
         based on ABRT_VER in order to avoid a very old alias for misa that
         duplicates the name "misa" but at a different CSR address.  */
#define DECLARE_CSR_ALIAS(NAME,VALUE,CLASS,DEF_VER,ABRT_VER)     \
      if (csr_num == VALUE && ABRT_VER >= PRIV_SPEC_CLASS_1P11)  \
        reg.names.push_back ( # NAME );
#include "opcode/riscv-opc.h"
#undef DECLARE_CSR_ALIAS
    }
}

> It doesn't really matter that we have two different registers with the
> same address, as long as the gdb client doesn't submit an XML file
> that tries to define both registers.  So a gdb client will send an xml
> file that says that either mucounteren or mcountinhibit exists, and
> gdb will map that to an address, and gdb doesn't have to know what the
> registers do, or that these are two different registers.

It seems that we can remove the aborted version checking in
riscv_create_csr_aliases directly.  And qemu have to make sure that
it's xml file won't try to define both CSR and it's aliases, which use
the same address but have different semantics.  I will check this with
Andrew Burgess, and make sure if this is in line with his original
idea and good to him, too :)

> From a binutils point of view, the only real problem is that disassembly will
> be wrong if we print the wrong register name, but that would require
> teaching the disassembler about priv spec versions which may not be
> worth the trouble.

Yeah, the only problem of binutils is how to teach gdb dis-assembler
about priv spec versions.


Thank you very much
Nelson


More information about the Binutils mailing list