git: 0d7e2e14ba79 - stable/14 - cxgbetool(8): Be flexible about the nexus name.
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Wed, 17 Jul 2024 14:21:53 UTC
The branch stable/14 has been updated by np: URL: https://cgit.FreeBSD.org/src/commit/?id=0d7e2e14ba79cac306959abc6d35b119ee1a38e8 commit 0d7e2e14ba79cac306959abc6d35b119ee1a38e8 Author: Navdeep Parhar <np@FreeBSD.org> AuthorDate: 2024-06-13 20:17:55 +0000 Commit: Navdeep Parhar <np@FreeBSD.org> CommitDate: 2024-07-17 06:39:56 +0000 cxgbetool(8): Be flexible about the nexus name. Use the name as-is but perform cxgbe specific ioctls on the device to make sure that it is a Terminator device nexus. Determine the chip type, pf/vf, etc. from the device registers rather than the nexus name. This allows cxgbetool to work with the VF driver. Sponsored by: Chelsio Communications (cherry picked from commit e827b61cacddd4bc9a2f1657ad8c6d2bcd70d52e) --- usr.sbin/cxgbetool/cxgbetool.c | 116 +++++++++++++++++++++++++++-------------- 1 file changed, 76 insertions(+), 40 deletions(-) diff --git a/usr.sbin/cxgbetool/cxgbetool.c b/usr.sbin/cxgbetool/cxgbetool.c index c02bc7fdc054..7b2b495a0292 100644 --- a/usr.sbin/cxgbetool/cxgbetool.c +++ b/usr.sbin/cxgbetool/cxgbetool.c @@ -43,6 +43,7 @@ #include <errno.h> #include <fcntl.h> #include <limits.h> +#include <stdbool.h> #include <stdint.h> #include <stdio.h> #include <stdlib.h> @@ -56,9 +57,16 @@ #define in_range(val, lo, hi) ( val < 0 || (val <= hi && val >= lo)) #define max(x, y) ((x) > (y) ? (x) : (y)) -static const char *progname, *nexus; -static int chip_id; /* 4 for T4, 5 for T5, and so on. */ -static int inst; /* instance of nexus device */ +static struct { + const char *progname, *nexus; + int chip_id; /* 4 for T4, 5 for T5, and so on. */ + int inst; /* instance of nexus device */ + int pf; /* PF# of the nexus (if not VF). */ + bool vf; /* Nexus is a VF. */ + + int fd; + bool warn_on_ioctl_err; +} g; struct reg_info { const char *name; @@ -88,7 +96,7 @@ struct field_desc { static void usage(FILE *fp) { - fprintf(fp, "Usage: %s <nexus> [operation]\n", progname); + fprintf(fp, "Usage: %s <nexus> [operation]\n", g.progname); fprintf(fp, "\tclearstats <port> clear port statistics\n" "\tclip hold|release <ip6> hold/release an address\n" @@ -137,27 +145,12 @@ get_card_vers(unsigned int version) static int real_doit(unsigned long cmd, void *data, const char *cmdstr) { - static int fd = -1; - int rc = 0; - - if (fd == -1) { - char buf[64]; - - snprintf(buf, sizeof(buf), "/dev/%s", nexus); - if ((fd = open(buf, O_RDWR)) < 0) { - warn("open(%s)", nexus); - rc = errno; - return (rc); - } - } - - rc = ioctl(fd, cmd, data); - if (rc < 0) { - warn("%s", cmdstr); - rc = errno; + if (ioctl(g.fd, cmd, data) < 0) { + if (g.warn_on_ioctl_err) + warn("%s", cmdstr); + return (errno); } - - return (rc); + return (0); } #define doit(x, y) real_doit(x, y, #x) @@ -523,7 +516,7 @@ dump_regs(int argc, const char *argv[]) rc = dump_regs_t6(argc, argv, regs.data); } else { warnx("%s (type %d, rev %d) is not a known card.", - nexus, vers, revision); + g.nexus, vers, revision); return (ENOTSUP); } @@ -915,7 +908,7 @@ do_show_one_filter_info(struct t4_filter *t, uint32_t mode) printf("(hash)"); } } - if (chip_id <= 5 && t->fs.prio) + if (g.chip_id <= 5 && t->fs.prio) printf(" Prio"); if (t->fs.rpttid) printf(" RptTID"); @@ -934,7 +927,7 @@ show_filters(int hash) if (rc != 0) return (rc); - if (!hash && chip_id >= 6) { + if (!hash && g.chip_id >= 6) { header = 0; bzero(&t, sizeof (t)); t.idx = 0; @@ -1925,10 +1918,10 @@ get_sge_context(int argc, const char *argv[]) if (rc != 0) return (rc); - if (chip_id == 4) + if (g.chip_id == 4) show_t4_ctxt(&cntxt); else - show_t5t6_ctxt(&cntxt, chip_id); + show_t5t6_ctxt(&cntxt, g.chip_id); return (0); } @@ -2244,7 +2237,7 @@ show_tcb(uint32_t *buf, uint32_t len) } printf("\n"); } - set_tcb_info(TIDTYPE_TCB, chip_id); + set_tcb_info(TIDTYPE_TCB, g.chip_id); set_print_style(PRNTSTYL_COMP); swizzle_tcb(tcb); parse_n_display_xcb(tcb); @@ -2448,7 +2441,7 @@ static void create_tracing_ifnet() { char *cmd[] = { - "/sbin/ifconfig", __DECONST(char *, nexus), "create", NULL + "/sbin/ifconfig", __DECONST(char *, g.nexus), "create", NULL }; char *env[] = {NULL}; @@ -3495,7 +3488,7 @@ display_clip(void) return (errno); } - snprintf(name, sizeof(name), "dev.t%unex.%u.misc.clip", chip_id, inst); + snprintf(name, sizeof(name), "dev.t%unex.%u.misc.clip", g.chip_id, g.inst); rc = sysctlbyname(name, buf, &clip_buf_size, NULL, 0); if (rc != 0) { warn("sysctl %s", name); @@ -3650,14 +3643,57 @@ run_cmd_loop(void) return (rc); } +#define A_PL_WHOAMI 0x19400 +#define A_PL_REV 0x1943c +#define A_PL_VF_WHOAMI 0x200 +#define A_PL_VF_REV 0x204 + static void -parse_nexus_name(const char *s) +open_nexus_device(const char *s) { - char junk; - - if (sscanf(s, "t%unex%u%c", &chip_id, &inst, &junk) != 2) - errx(EINVAL, "invalid nexus \"%s\"", s); - nexus = s; + const int len = strlen(s); + long long val; + const char *num; + int rc; + u_int chip_id, whoami; + char buf[128]; + + if (len < 2 || isdigit(s[0]) || !isdigit(s[len - 1])) + errx(1, "invalid nexus name \"%s\"", s); + for (num = s + len - 1; isdigit(*num); num--) + continue; + g.inst = strtoll(num, NULL, 0); + g.nexus = s; + snprintf(buf, sizeof(buf), "/dev/%s", g.nexus); + if ((g.fd = open(buf, O_RDWR)) < 0) + err(1, "open(%s)", buf); + + g.warn_on_ioctl_err = false; + rc = read_reg(A_PL_REV, 4, &val); + if (rc == 0) { + /* PF */ + g.vf = false; + whoami = A_PL_WHOAMI; + } else { + rc = read_reg(A_PL_VF_REV, 4, &val); + if (rc != 0) + errx(1, "%s is not a Terminator device.", s); + /* VF */ + g.vf = true; + whoami = A_PL_VF_WHOAMI; + } + chip_id = (val >> 4) & 0xf; + if (chip_id == 0) + chip_id = 4; + if (chip_id < 4 || chip_id > 7) + warnx("%s reports chip_id %d.", s, chip_id); + g.chip_id = chip_id; + + rc = read_reg(whoami, 4, &val); + if (rc != 0) + errx(rc, "failed to read whoami(0x%x): %d", whoami, rc); + g.pf = g.chip_id > 5 ? (val >> 9) & 7 : (val >> 8) & 7; + g.warn_on_ioctl_err = true; } int @@ -3665,7 +3701,7 @@ main(int argc, const char *argv[]) { int rc = -1; - progname = argv[0]; + g.progname = argv[0]; if (argc == 2) { if (!strcmp(argv[1], "-h") || !strcmp(argv[1], "--help")) { @@ -3679,7 +3715,7 @@ main(int argc, const char *argv[]) exit(EINVAL); } - parse_nexus_name(argv[1]); + open_nexus_device(argv[1]); /* progname and nexus */ argc -= 2;