qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
From: Alistair Francis <alistair23@gmail.com>
To: "Daniel P. Berrangé" <berrange@redhat.com>
Cc: Alistair Francis <Alistair.Francis@wdc.com>,
	"qemu-devel@nongnu.org" <qemu-devel@nongnu.org>,
	"qemu-riscv@nongnu.org" <qemu-riscv@nongnu.org>,
	"palmer@sifive.com" <palmer@sifive.com>,
	"ijc@hellion.org.uk" <ijc@hellion.org.uk>
Subject: Re: [Qemu-devel] [PATCH for 4.1 v3 2/6] target/riscv: Fall back to generating a RISC-V CPU
Date: Fri, 19 Apr 2019 13:55:10 -0700	[thread overview]
Message-ID: <CAKmqyKPNNVGuH4veQKLuNQ3PFAko9eDeqdmF-zHmDG_9Kp_tDA@mail.gmail.com> (raw)
In-Reply-To: <20190416132337.GN31311@redhat.com>

On Tue, Apr 16, 2019 at 6:23 AM Daniel P. Berrangé <berrange@redhat.com> wrote:
>
> On Wed, Apr 10, 2019 at 11:10:25PM +0000, Alistair Francis wrote:
> > If a user specifies a CPU that we don't understand then we want to fall
> > back to a CPU generated from the ISA string.
> >
> > At the moment the generated CPU is assumed to be a privledge spec
> > version 1.10 CPU with an MMU. This can be changed in the future.
> >
> > Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
> > ---
> > v3:
> >  - Ensure a minimal length so we don't run off the end of the string.
> >  - Don't parse the rv32/rv64 in the loop
> >  target/riscv/cpu.c | 101 ++++++++++++++++++++++++++++++++++++++++++++-
> >  target/riscv/cpu.h |   2 +
> >  2 files changed, 102 insertions(+), 1 deletion(-)
> >
> > diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
> > index d61bce6d55..27be9e412a 100644
> > --- a/target/riscv/cpu.c
> > +++ b/target/riscv/cpu.c
> > @@ -19,6 +19,7 @@
> >
> >  #include "qemu/osdep.h"
> >  #include "qemu/log.h"
> > +#include "qemu/error-report.h"
> >  #include "cpu.h"
> >  #include "exec/exec-all.h"
> >  #include "qapi/error.h"
> > @@ -103,6 +104,99 @@ static void set_resetvec(CPURISCVState *env, int resetvec)
> >  #endif
> >  }
> >
> > +static void riscv_generate_cpu_init(Object *obj)
> > +{
> > +    RISCVCPU *cpu = RISCV_CPU(obj);
> > +    CPURISCVState *env = &cpu->env;
> > +    RISCVCPUClass *mcc = RISCV_CPU_GET_CLASS(cpu);
> > +    const char *riscv_cpu = mcc->isa_str;
> > +    target_ulong target_misa = 0;
> > +    target_ulong rvxlen = 0;
> > +    int i;
> > +    bool valid = false;
> > +
> > +    /*
> > +     * We need at least 5 charecters for the string to be valid. Check that
> > +     * now so we can be lazier later.
> > +     */
> > +    if (strlen(riscv_cpu) < 5) {
> > +        error_report("'%s' does not appear to be a valid RISC-V ISA string",
> > +                     riscv_cpu);
> > +        exit(1);
> > +    }
> > +
> > +    if (riscv_cpu[0] == 'r' && riscv_cpu[1] == 'v') {
> > +        /* Starts with "rv" */
> > +        if (riscv_cpu[2] == '3' && riscv_cpu[3] == '2') {
> > +            valid = true;
> > +            rvxlen = RV32;
> > +        }
> > +        if (riscv_cpu[2] == '6' && riscv_cpu[3] == '4') {
> > +            valid = true;
> > +            rvxlen = RV64;
> > +        }
> > +    }
> > +
> > +    if (!valid) {
> > +        error_report("'%s' does not appear to be a valid RISC-V CPU",
> > +                     riscv_cpu);
> > +        exit(1);
> > +    }
> > +
> > +    for (i = 4; i < strlen(riscv_cpu); i++) {
> > +        switch (riscv_cpu[i]) {
> > +        case 'i':
> > +            if (target_misa & RVE) {
> > +                error_report("I and E extensions are incompatible");
> > +                exit(1);
> > +            }
> > +            target_misa |= RVI;
> > +            continue;
> > +        case 'e':
> > +            if (target_misa & RVI) {
> > +                error_report("I and E extensions are incompatible");
> > +                exit(1);
> > +            }
> > +            target_misa |= RVE;
> > +            continue;
> > +        case 'g':
> > +            target_misa |= RVI | RVM | RVA | RVF | RVD;
> > +            continue;
> > +        case 'm':
> > +            target_misa |= RVM;
> > +            continue;
> > +        case 'a':
> > +            target_misa |= RVA;
> > +            continue;
> > +        case 'f':
> > +            target_misa |= RVF;
> > +            continue;
> > +        case 'd':
> > +            target_misa |= RVD;
> > +            continue;
> > +        case 'c':
> > +            target_misa |= RVC;
> > +            continue;
> > +        case 's':
> > +            target_misa |= RVS;
> > +            continue;
> > +        case 'u':
> > +            target_misa |= RVU;
> > +            continue;
> > +        default:
> > +            warn_report("QEMU does not support the %c extension",
> > +                        riscv_cpu[i]);
> > +            continue;
> > +        }
> > +    }
> > +
> > +    set_misa(env, rvxlen | target_misa);
> > +    set_versions(env, USER_VERSION_2_02_0, PRIV_VERSION_1_10_0);
> > +    set_resetvec(env, DEFAULT_RSTVEC);
> > +    set_feature(env, RISCV_FEATURE_MMU);
> > +    set_feature(env, RISCV_FEATURE_PMP);
> > +}
>
> This whole approach feels undesirable to me, as it is quite different to
> way CPUs are represented in the other architectures in QEMU and as a result
> does not fit in the QAPI commands we've been building in QEMU for dealing
> with CPU model representation. This will make for increased maint burden
> in both QEMU and apps managing QEMU
>
> IIUC, this code is taking an arbitrary CPU model string and looking
> at individual characters in that string & turning on individual features
> according to what characters it sees. There's several problems with this
>
>  - There's no way to enumerate valid CPU model names
>
>  - There can be many different names that all result
>    in the same CPU model. eg "fdcs", "scdf", a"ffddccss"
>    all result in the same features getting enabled
>    by this loop above.
>
>  - There's no way to check compatibility between CPUs
>
>  - There will be no way to version the CPUs if we need
>    to tie them to machine types for back compatibility.
>
> If we have a base CPU model, with a bunch of features that can optionally
> be enabled, then IMHO we should represent that the same way was we do
> on x86, whre we have a CPU model name, and then a comma sepaprated list
> of features.
>
> If on the other hand we don't want to support the combinatorial matrix
> of all possible feature flags, then we should just list all the expected
> named CPU models that are required explicitly.

Ok, I'm about to send out a new series that is based on this series.
The new series is called "RISC-V: Add properties to the CPUs". It has
dropped the ISA string part (this patch) and just adds some standard
CPU properties. If everyone is happy with that approach I'll continue
to expand it to add the extensions as CPU properties.

Alistair

>
> Regards,
> Daniel
> --
> |: https://berrange.com      -o-    https://www.flickr.com/photos/dberrange :|
> |: https://libvirt.org         -o-            https://fstop138.berrange.com :|
> |: https://entangle-photo.org    -o-    https://www.instagram.com/dberrange :|

WARNING: multiple messages have this Message-ID (diff)
From: Alistair Francis <alistair23@gmail.com>
To: "Daniel P. Berrangé" <berrange@redhat.com>
Cc: "qemu-riscv@nongnu.org" <qemu-riscv@nongnu.org>,
	"palmer@sifive.com" <palmer@sifive.com>,
	Alistair Francis <Alistair.Francis@wdc.com>,
	"qemu-devel@nongnu.org" <qemu-devel@nongnu.org>,
	"ijc@hellion.org.uk" <ijc@hellion.org.uk>
Subject: Re: [Qemu-devel] [PATCH for 4.1 v3 2/6] target/riscv: Fall back to generating a RISC-V CPU
Date: Fri, 19 Apr 2019 13:55:10 -0700	[thread overview]
Message-ID: <CAKmqyKPNNVGuH4veQKLuNQ3PFAko9eDeqdmF-zHmDG_9Kp_tDA@mail.gmail.com> (raw)
Message-ID: <20190419205510.m0VHt4Tm7huvxEMrJ_a8cTn_gHQfJDEs19U8OiZc4Xw@z> (raw)
In-Reply-To: <20190416132337.GN31311@redhat.com>

On Tue, Apr 16, 2019 at 6:23 AM Daniel P. Berrangé <berrange@redhat.com> wrote:
>
> On Wed, Apr 10, 2019 at 11:10:25PM +0000, Alistair Francis wrote:
> > If a user specifies a CPU that we don't understand then we want to fall
> > back to a CPU generated from the ISA string.
> >
> > At the moment the generated CPU is assumed to be a privledge spec
> > version 1.10 CPU with an MMU. This can be changed in the future.
> >
> > Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
> > ---
> > v3:
> >  - Ensure a minimal length so we don't run off the end of the string.
> >  - Don't parse the rv32/rv64 in the loop
> >  target/riscv/cpu.c | 101 ++++++++++++++++++++++++++++++++++++++++++++-
> >  target/riscv/cpu.h |   2 +
> >  2 files changed, 102 insertions(+), 1 deletion(-)
> >
> > diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
> > index d61bce6d55..27be9e412a 100644
> > --- a/target/riscv/cpu.c
> > +++ b/target/riscv/cpu.c
> > @@ -19,6 +19,7 @@
> >
> >  #include "qemu/osdep.h"
> >  #include "qemu/log.h"
> > +#include "qemu/error-report.h"
> >  #include "cpu.h"
> >  #include "exec/exec-all.h"
> >  #include "qapi/error.h"
> > @@ -103,6 +104,99 @@ static void set_resetvec(CPURISCVState *env, int resetvec)
> >  #endif
> >  }
> >
> > +static void riscv_generate_cpu_init(Object *obj)
> > +{
> > +    RISCVCPU *cpu = RISCV_CPU(obj);
> > +    CPURISCVState *env = &cpu->env;
> > +    RISCVCPUClass *mcc = RISCV_CPU_GET_CLASS(cpu);
> > +    const char *riscv_cpu = mcc->isa_str;
> > +    target_ulong target_misa = 0;
> > +    target_ulong rvxlen = 0;
> > +    int i;
> > +    bool valid = false;
> > +
> > +    /*
> > +     * We need at least 5 charecters for the string to be valid. Check that
> > +     * now so we can be lazier later.
> > +     */
> > +    if (strlen(riscv_cpu) < 5) {
> > +        error_report("'%s' does not appear to be a valid RISC-V ISA string",
> > +                     riscv_cpu);
> > +        exit(1);
> > +    }
> > +
> > +    if (riscv_cpu[0] == 'r' && riscv_cpu[1] == 'v') {
> > +        /* Starts with "rv" */
> > +        if (riscv_cpu[2] == '3' && riscv_cpu[3] == '2') {
> > +            valid = true;
> > +            rvxlen = RV32;
> > +        }
> > +        if (riscv_cpu[2] == '6' && riscv_cpu[3] == '4') {
> > +            valid = true;
> > +            rvxlen = RV64;
> > +        }
> > +    }
> > +
> > +    if (!valid) {
> > +        error_report("'%s' does not appear to be a valid RISC-V CPU",
> > +                     riscv_cpu);
> > +        exit(1);
> > +    }
> > +
> > +    for (i = 4; i < strlen(riscv_cpu); i++) {
> > +        switch (riscv_cpu[i]) {
> > +        case 'i':
> > +            if (target_misa & RVE) {
> > +                error_report("I and E extensions are incompatible");
> > +                exit(1);
> > +            }
> > +            target_misa |= RVI;
> > +            continue;
> > +        case 'e':
> > +            if (target_misa & RVI) {
> > +                error_report("I and E extensions are incompatible");
> > +                exit(1);
> > +            }
> > +            target_misa |= RVE;
> > +            continue;
> > +        case 'g':
> > +            target_misa |= RVI | RVM | RVA | RVF | RVD;
> > +            continue;
> > +        case 'm':
> > +            target_misa |= RVM;
> > +            continue;
> > +        case 'a':
> > +            target_misa |= RVA;
> > +            continue;
> > +        case 'f':
> > +            target_misa |= RVF;
> > +            continue;
> > +        case 'd':
> > +            target_misa |= RVD;
> > +            continue;
> > +        case 'c':
> > +            target_misa |= RVC;
> > +            continue;
> > +        case 's':
> > +            target_misa |= RVS;
> > +            continue;
> > +        case 'u':
> > +            target_misa |= RVU;
> > +            continue;
> > +        default:
> > +            warn_report("QEMU does not support the %c extension",
> > +                        riscv_cpu[i]);
> > +            continue;
> > +        }
> > +    }
> > +
> > +    set_misa(env, rvxlen | target_misa);
> > +    set_versions(env, USER_VERSION_2_02_0, PRIV_VERSION_1_10_0);
> > +    set_resetvec(env, DEFAULT_RSTVEC);
> > +    set_feature(env, RISCV_FEATURE_MMU);
> > +    set_feature(env, RISCV_FEATURE_PMP);
> > +}
>
> This whole approach feels undesirable to me, as it is quite different to
> way CPUs are represented in the other architectures in QEMU and as a result
> does not fit in the QAPI commands we've been building in QEMU for dealing
> with CPU model representation. This will make for increased maint burden
> in both QEMU and apps managing QEMU
>
> IIUC, this code is taking an arbitrary CPU model string and looking
> at individual characters in that string & turning on individual features
> according to what characters it sees. There's several problems with this
>
>  - There's no way to enumerate valid CPU model names
>
>  - There can be many different names that all result
>    in the same CPU model. eg "fdcs", "scdf", a"ffddccss"
>    all result in the same features getting enabled
>    by this loop above.
>
>  - There's no way to check compatibility between CPUs
>
>  - There will be no way to version the CPUs if we need
>    to tie them to machine types for back compatibility.
>
> If we have a base CPU model, with a bunch of features that can optionally
> be enabled, then IMHO we should represent that the same way was we do
> on x86, whre we have a CPU model name, and then a comma sepaprated list
> of features.
>
> If on the other hand we don't want to support the combinatorial matrix
> of all possible feature flags, then we should just list all the expected
> named CPU models that are required explicitly.

Ok, I'm about to send out a new series that is based on this series.
The new series is called "RISC-V: Add properties to the CPUs". It has
dropped the ISA string part (this patch) and just adds some standard
CPU properties. If everyone is happy with that approach I'll continue
to expand it to add the extensions as CPU properties.

Alistair

>
> Regards,
> Daniel
> --
> |: https://berrange.com      -o-    https://www.flickr.com/photos/dberrange :|
> |: https://libvirt.org         -o-            https://fstop138.berrange.com :|
> |: https://entangle-photo.org    -o-    https://www.instagram.com/dberrange :|


  parent reply	other threads:[~2019-04-19 20:55 UTC|newest]

Thread overview: 46+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2019-04-10 23:10 [Qemu-devel] [PATCH for 4.1 v3 0/6] RISC-V: Allow specifying CPU ISA via command line Alistair Francis
2019-04-10 23:10 ` Alistair Francis
2019-04-10 23:10 ` [Qemu-devel] [PATCH for 4.1 v3 1/6] linux-user/riscv: Add the CPU type as a comment Alistair Francis
2019-04-10 23:10   ` Alistair Francis
2019-04-10 23:10 ` [Qemu-devel] [PATCH for 4.1 v3 2/6] target/riscv: Fall back to generating a RISC-V CPU Alistair Francis
2019-04-10 23:10   ` Alistair Francis
2019-04-11 12:18   ` Igor Mammedov
2019-04-11 12:18     ` Igor Mammedov
2019-04-11 20:42     ` Alistair Francis
2019-04-11 20:42       ` Alistair Francis
2019-04-12  8:35       ` Igor Mammedov
2019-04-12  8:35         ` Igor Mammedov
2019-04-12 21:19         ` Alistair Francis
2019-04-12 21:19           ` Alistair Francis
2019-04-15  8:38           ` Igor Mammedov
2019-04-15  8:38             ` Igor Mammedov
2019-04-15 23:56             ` Alistair Francis
2019-04-15 23:56               ` Alistair Francis
2019-04-16 12:19               ` Igor Mammedov
2019-04-16 12:19                 ` Igor Mammedov
2019-04-16 13:23   ` Daniel P. Berrangé
2019-04-16 13:23     ` Daniel P. Berrangé
2019-04-19 20:55     ` Alistair Francis [this message]
2019-04-19 20:55       ` Alistair Francis
2019-04-10 23:10 ` [Qemu-devel] [PATCH for 4.1 v3 3/6] target/riscv: Create settable CPU properties Alistair Francis
2019-04-10 23:10   ` Alistair Francis
2019-04-10 23:10 ` [Qemu-devel] [PATCH for 4.1 v3 4/6] riscv: virt: Allow specifying a CPU via commandline Alistair Francis
2019-04-10 23:10   ` Alistair Francis
2019-04-11 11:53   ` Igor Mammedov
2019-04-11 11:53     ` Igor Mammedov
2019-04-10 23:10 ` [Qemu-devel] [PATCH for 4.1 v3 5/6] target/riscv: Remove the generic no MMU CPUs Alistair Francis
2019-04-10 23:10   ` Alistair Francis
2019-04-10 23:11 ` [Qemu-devel] [PATCH for 4.1 v3 6/6] riscv: Add a generic spike machine Alistair Francis
2019-04-10 23:11   ` Alistair Francis
2019-04-11 12:06   ` Igor Mammedov
2019-04-11 12:06     ` Igor Mammedov
2019-04-11 12:18     ` Peter Maydell
2019-04-11 12:18       ` Peter Maydell
2019-04-11 20:35       ` Alistair Francis
2019-04-11 20:35         ` Alistair Francis
2019-04-12  7:46         ` Ian Campbell
2019-04-12  7:46           ` Ian Campbell
2019-04-11 20:34     ` Alistair Francis
2019-04-11 20:34       ` Alistair Francis
2019-04-12  8:38       ` Igor Mammedov
2019-04-12  8:38         ` Igor Mammedov

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=CAKmqyKPNNVGuH4veQKLuNQ3PFAko9eDeqdmF-zHmDG_9Kp_tDA@mail.gmail.com \
    --to=alistair23@gmail.com \
    --cc=Alistair.Francis@wdc.com \
    --cc=berrange@redhat.com \
    --cc=ijc@hellion.org.uk \
    --cc=palmer@sifive.com \
    --cc=qemu-devel@nongnu.org \
    --cc=qemu-riscv@nongnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).