Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/arch/alpha Expose a bunch of CPU details, including impl...



details:   https://anonhg.NetBSD.org/src/rev/c3efe8825338
branches:  trunk
changeset: 1015120:c3efe8825338
user:      thorpej <thorpej%NetBSD.org@localhost>
date:      Thu Oct 15 01:00:01 2020 +0000

description:
Expose a bunch of CPU details, including implementation version and
architecture extensions, via sysctl:

hw.cpu0.model = 21264A-0 (EV67)
hw.cpu0.major = 11
hw.cpu0.minor = 0
hw.cpu0.implver = 2
hw.cpu0.amask = 0x1307
hw.cpu0.bwx = 1
hw.cpu0.fix = 1
hw.cpu0.cix = 1
hw.cpu0.mvi = 1
hw.cpu0.pat = 1
hw.cpu0.pmi = 1
hw.cpu0.vax_fp = 1
hw.cpu0.ieee_fp = 1
hw.cpu0.primary_eligible = 1
hw.cpu0.primary = 1
hw.cpu0.cpu_id = 0
hw.cpu0.pcc_freq = 239990688

as well as some potentially interesting system-level variables:

machdep.cctr = 0
machdep.is_qemu = 1

Should address the basic concern in PR port-alpha/15835.

diffstat:

 sys/arch/alpha/alpha/cpu.c      |  378 +++++++++++++++++++++++++++++++++------
 sys/arch/alpha/alpha/machdep.c  |   14 +-
 sys/arch/alpha/include/cpu.h    |    5 +-
 sys/arch/alpha/include/cpuvar.h |   17 +-
 4 files changed, 348 insertions(+), 66 deletions(-)

diffs (truncated from 600 to 300 lines):

diff -r 0b94f20c6301 -r c3efe8825338 sys/arch/alpha/alpha/cpu.c
--- a/sys/arch/alpha/alpha/cpu.c        Thu Oct 15 00:55:09 2020 +0000
+++ b/sys/arch/alpha/alpha/cpu.c        Thu Oct 15 01:00:01 2020 +0000
@@ -1,7 +1,7 @@
-/* $NetBSD: cpu.c,v 1.102 2020/10/10 03:05:04 thorpej Exp $ */
+/* $NetBSD: cpu.c,v 1.103 2020/10/15 01:00:01 thorpej Exp $ */
 
 /*-
- * Copyright (c) 1998, 1999, 2000, 2001 The NetBSD Foundation, Inc.
+ * Copyright (c) 1998, 1999, 2000, 2001, 2020 The NetBSD Foundation, Inc.
  * All rights reserved.
  *
  * This code is derived from software contributed to The NetBSD Foundation
@@ -59,7 +59,7 @@
 
 #include <sys/cdefs.h>                 /* RCS ID & Copyright macro defns */
 
-__KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.102 2020/10/10 03:05:04 thorpej Exp $");
+__KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.103 2020/10/15 01:00:01 thorpej Exp $");
 
 #include "opt_ddb.h"
 #include "opt_multiprocessor.h"
@@ -71,6 +71,7 @@
 #include <sys/proc.h>
 #include <sys/atomic.h>
 #include <sys/cpu.h>
+#include <sys/sysctl.h>
 
 #include <uvm/uvm_extern.h>
 
@@ -147,33 +148,151 @@
        "",
        "21066", "21066",
        "21068", "21068",
-       "21066A", "21068A", 0
+       "21066A", "21068A",
+       NULL
 };
 
 const struct cputable_struct {
-       int     cpu_major_code;
+       const char *cpu_evname;
        const char *cpu_major_name;
        const char * const *cpu_minor_names;
 } cpunametable[] = {
-       { PCS_PROC_EV3,         "EV3",          NULL            },
-       { PCS_PROC_EV4,         "21064",        NULL            },
-       { PCS_PROC_SIMULATION,  "Sim",          NULL            },
-       { PCS_PROC_LCA4,        "LCA",          lcaminor        },
-       { PCS_PROC_EV5,         "21164",        NULL            },
-       { PCS_PROC_EV45,        "21064A",       NULL            },
-       { PCS_PROC_EV56,        "21164A",       NULL            },
-       { PCS_PROC_EV6,         "21264",        NULL            },
-       { PCS_PROC_PCA56,       "PCA56",        NULL            },
-       { PCS_PROC_PCA57,       "PCA57",        NULL            },
-       { PCS_PROC_EV67,        "21264A",       NULL            },
-       { PCS_PROC_EV68CB,      "21264C",       NULL            },
-       { PCS_PROC_EV68AL,      "21264B",       NULL            },
-       { PCS_PROC_EV68CX,      "21264D",       NULL            },
-       { PCS_PROC_EV7,         "21364",        NULL            },
-       { PCS_PROC_EV79,        "EV79",         NULL            },
-       { PCS_PROC_EV69,        "EV69",         NULL            },
+[PCS_PROC_EV3]       ={        "EV3",          NULL,           NULL            },
+[PCS_PROC_EV4]       ={        "EV4",          "21064",        NULL            },
+[PCS_PROC_SIMULATION]={ "Sim",         NULL,           NULL            },
+[PCS_PROC_LCA4]      ={        "LCA4",         NULL,           lcaminor        },
+[PCS_PROC_EV5]       ={        "EV5",          "21164",        NULL            },
+[PCS_PROC_EV45]      ={        "EV45",         "21064A",       NULL            },
+[PCS_PROC_EV56]      ={        "EV56",         "21164A",       NULL            },
+[PCS_PROC_EV6]       ={        "EV6",          "21264",        NULL            },
+[PCS_PROC_PCA56]     ={        "PCA56",        "21164PC",      NULL            },
+[PCS_PROC_PCA57]     ={        "PCA57",        "21164PC"/*XXX*/,NULL           },
+[PCS_PROC_EV67]      ={        "EV67",         "21264A",       NULL            },
+[PCS_PROC_EV68CB]    ={        "EV68CB",       "21264C",       NULL            },
+[PCS_PROC_EV68AL]    ={        "EV68AL",       "21264B",       NULL            },
+[PCS_PROC_EV68CX]    ={        "EV68CX",       "21264D",       NULL            },
+[PCS_PROC_EV7]       ={        "EV7",          "21364",        NULL            },
+[PCS_PROC_EV79]      ={        "EV79",         NULL,           NULL            },
+[PCS_PROC_EV69]      ={        "EV69",         NULL,           NULL            },
 };
 
+static bool
+cpu_description(const struct cpu_softc * const sc,
+    char * const buf, size_t const buflen)
+{
+       const char * const *s;
+       const char *ev;
+       int i;
+
+       const uint32_t major = sc->sc_major_type;
+       const uint32_t minor = sc->sc_minor_type;
+
+       if (major < __arraycount(cpunametable) &&
+           (ev = cpunametable[major].cpu_evname) != NULL) {
+               s = cpunametable[major].cpu_minor_names;
+               for (i = 0; s != NULL && s[i] != NULL; i++) {
+                       if (i == minor && strlen(s[i]) != 0) {
+                               break;
+                       }
+               }
+               if (s == NULL || s[i] == NULL) {
+                       s = &cpunametable[major].cpu_major_name;
+                       i = 0;
+                       if (s[i] == NULL) {
+                               s = NULL;
+                       }
+               }
+
+               /*
+                * Example strings:
+                *
+                *      Sim-0
+                *      21068-3 (LCA4)          [uses minor table]
+                *      21264C-5 (EV68CB)
+                *      21164PC-1 (PCA56)
+                */
+               if (s != NULL) {
+                       snprintf(buf, buflen, "%s-%d (%s)", s[i], minor, ev);
+               } else {
+                       snprintf(buf, buflen, "%s-%d", ev, minor);
+               }
+               return true;
+       }
+
+       snprintf(buf, buflen, "UNKNOWN CPU TYPE (%u:%u)", major, minor);
+       return false;
+}
+
+static int
+cpu_sysctl_model(SYSCTLFN_ARGS)
+{
+       struct sysctlnode node = *rnode;
+       const struct cpu_softc * const sc = node.sysctl_data;
+       char model[32];
+
+       cpu_description(sc, model, sizeof(model));
+       node.sysctl_data = model;
+       return sysctl_lookup(SYSCTLFN_CALL(&node));
+}
+
+static int
+cpu_sysctl_amask_bit(SYSCTLFN_ARGS, unsigned long const bit)
+{
+       struct sysctlnode node = *rnode;
+       const struct cpu_softc * const sc = node.sysctl_data;
+
+       bool result = (sc->sc_amask & bit) ? true : false;
+       node.sysctl_data = &result;
+       return sysctl_lookup(SYSCTLFN_CALL(&node));
+}
+
+static int
+cpu_sysctl_bwx(SYSCTLFN_ARGS)
+{
+       return cpu_sysctl_amask_bit(SYSCTLFN_CALL(rnode), ALPHA_AMASK_BWX);
+}
+
+static int
+cpu_sysctl_fix(SYSCTLFN_ARGS)
+{
+       return cpu_sysctl_amask_bit(SYSCTLFN_CALL(rnode), ALPHA_AMASK_FIX);
+}
+
+static int
+cpu_sysctl_cix(SYSCTLFN_ARGS)
+{
+       return cpu_sysctl_amask_bit(SYSCTLFN_CALL(rnode), ALPHA_AMASK_CIX);
+}
+
+static int
+cpu_sysctl_mvi(SYSCTLFN_ARGS)
+{
+       return cpu_sysctl_amask_bit(SYSCTLFN_CALL(rnode), ALPHA_AMASK_MVI);
+}
+
+static int
+cpu_sysctl_pat(SYSCTLFN_ARGS)
+{
+       return cpu_sysctl_amask_bit(SYSCTLFN_CALL(rnode), ALPHA_AMASK_PAT);
+}
+
+static int
+cpu_sysctl_pmi(SYSCTLFN_ARGS)
+{
+       return cpu_sysctl_amask_bit(SYSCTLFN_CALL(rnode), ALPHA_AMASK_PMI);
+}
+
+static int
+cpu_sysctl_primary(SYSCTLFN_ARGS)
+{
+       struct sysctlnode node = *rnode;
+       const struct cpu_softc * const sc = node.sysctl_data;
+
+       bool result = CPU_IS_PRIMARY(sc->sc_ci);
+       node.sysctl_data = &result;
+       return sysctl_lookup(SYSCTLFN_CALL(&node));
+}
+
 /*
  * The following is an attempt to map out how booting secondary CPUs
  * works.
@@ -219,43 +338,30 @@
 cpuattach(device_t parent, device_t self, void *aux)
 {
        struct cpu_softc * const sc = device_private(self);
-       struct mainbus_attach_args *ma = aux;
-       int i;
-       const char * const *s;
-       struct pcs *p;
-       uint32_t major, minor;
+       const struct mainbus_attach_args * const ma = aux;
        struct cpu_info *ci;
+       char model[32];
+
+       const bool primary = ma->ma_slot == hwrpb->rpb_primary_cpu_id;
 
        sc->sc_dev = self;
 
-       p = LOCATE_PCS(hwrpb, ma->ma_slot);
-       major = PCS_CPU_MAJORTYPE(p);
-       minor = PCS_CPU_MINORTYPE(p);
+       const struct pcs * const p = LOCATE_PCS(hwrpb, ma->ma_slot);
+       sc->sc_major_type = PCS_CPU_MAJORTYPE(p);
+       sc->sc_minor_type = PCS_CPU_MINORTYPE(p);
 
-       aprint_normal(": ID %d%s, ", ma->ma_slot,
-           ma->ma_slot == hwrpb->rpb_primary_cpu_id ? " (primary)" : "");
+       const bool recognized = cpu_description(sc, model, sizeof(model));
 
-       for(i = 0; i < __arraycount(cpunametable); ++i) {
-               if (cpunametable[i].cpu_major_code == major) {
-                       aprint_normal("%s-%d",
-                           cpunametable[i].cpu_major_name, minor);
-                       s = cpunametable[i].cpu_minor_names;
-                       for(i = 0; s && s[i]; ++i) {
-                               if (i == minor && strlen(s[i]) != 0) {
-                                       aprint_normal(" (%s)", s[i]);
-                                       goto recognized;
-                               }
-                       }
-                       goto recognized;
-               }
+       aprint_normal(": ID %d%s, ", ma->ma_slot, primary ? " (primary)" : "");
+       if (recognized) {
+               aprint_normal("%s", model);
+       } else {
+               aprint_error("%s", model);
        }
-       aprint_error("UNKNOWN CPU TYPE (%d:%d)", major, minor);
 
-recognized:
        aprint_naive("\n");
        aprint_normal("\n");
 
-#ifdef DEBUG
        if (p->pcs_proc_var != 0) {
                bool needcomma = false;
                const char *vaxfp = "";
@@ -263,16 +369,19 @@
                const char *pe = "";
 
                if (p->pcs_proc_var & PCS_VAR_VAXFP) {
+                       sc->sc_vax_fp = true;
                        vaxfp = "VAX FP support";
                        needcomma = true;
                }
                if (p->pcs_proc_var & PCS_VAR_IEEEFP) {
+                       sc->sc_ieee_fp = true;
                        ieeefp = ", IEEE FP support";
                        if (!needcomma)
                                ieeefp += 2;
                        needcomma = true;
                }
                if (p->pcs_proc_var & PCS_VAR_PE) {
+                       sc->sc_primary_eligible = true;
                        pe = ", Primary Eligible";
                        if (!needcomma)
                                pe += 2;
@@ -285,19 +394,18 @@
                            p->pcs_proc_var & PCS_VAR_RESERVED);
                aprint_debug("\n");
        }
-#endif
 
        if (ma->ma_slot > ALPHA_WHAMI_MAXID) {
-               if (ma->ma_slot == hwrpb->rpb_primary_cpu_id)
+               if (primary)
                        panic("cpu_attach: primary CPU ID too large");
                aprint_error_dev(sc->sc_dev,
                    "processor ID too large, ignoring\n");
                return;
        }
 
-       if (ma->ma_slot == hwrpb->rpb_primary_cpu_id)
+       if (primary) {
                ci = &cpu_info_primary;
-       else {
+       } else {
                /*
                 * kmem_zalloc() will guarante cache line alignment for



Home | Main Index | Thread Index | Old Index