cxgbetool(8): Userspace part of support for high priority filters on T6+.

MFC after:	1 week
Sponsored by:	Chelsio Communications
This commit is contained in:
Navdeep Parhar 2018-08-09 14:21:27 +00:00
parent 5fc0f72f3b
commit 6ba813531f
2 changed files with 70 additions and 12 deletions

View File

@ -31,7 +31,7 @@
.\"
.\" $FreeBSD$
.\"
.Dd May 14, 2018
.Dd Aug 8, 2018
.Dt CXGBETOOL 8
.Os
.Sh NAME
@ -60,7 +60,7 @@
.It
.Nm Ar nexus Cm filter Ar idx Ar filter-specification
.It
.Nm Ar nexus Cm filter Ar idx Cm delete
.Nm Ar nexus Cm filter Ar idx Cm delete Op Cm prio Bro Cm 0 | 1 Brc
.It
.Nm Ar nexus Cm filter list
.It
@ -381,7 +381,7 @@ TCAM filters: The number of available filters is in
dev.<nexus>.<instance>.nfilters.
.Ar idx
must be an unused index between 0 and nfilters - 1.
IPv6 filters consume 4 consecutive entries on T4/T5 and and 2 on T6 and
IPv6 filters consume 4 consecutive entries on T4/T5 and 2 on T6 and
.Ar idx
must be aligned to 4 or 2 in this case.
.Pp

View File

@ -94,7 +94,7 @@ usage(FILE *fp)
"\tcontext <type> <id> show an SGE context\n"
"\tdumpstate <dump.bin> dump chip state\n"
"\tfilter <idx> [<param> <val>] ... set a filter\n"
"\tfilter <idx> delete|clear delete a filter\n"
"\tfilter <idx> delete|clear [prio 1] delete a filter\n"
"\tfilter list list all filters\n"
"\tfilter mode [<match>] ... get/set global filter mode\n"
"\thashfilter [<param> <val>] ... set a hashfilter\n"
@ -147,7 +147,6 @@ real_doit(unsigned long cmd, void *data, const char *cmdstr)
rc = errno;
return (rc);
}
chip_id = nexus[1] - '0';
}
rc = ioctl(fd, cmd, data);
@ -934,7 +933,7 @@ do_show_one_filter_info(struct t4_filter *t, uint32_t mode)
printf("(hash)");
}
}
if (t->fs.prio)
if (chip_id <= 5 && t->fs.prio)
printf(" Prio");
if (t->fs.rpttid)
printf(" RptTID");
@ -944,7 +943,7 @@ do_show_one_filter_info(struct t4_filter *t, uint32_t mode)
static int
show_filters(int hash)
{
uint32_t mode = 0, header = 0;
uint32_t mode = 0, header, hpfilter = 0;
struct t4_filter t;
int rc;
@ -953,6 +952,29 @@ show_filters(int hash)
if (rc != 0)
return (rc);
if (!hash && chip_id >= 6) {
header = 0;
bzero(&t, sizeof (t));
t.idx = 0;
t.fs.hash = 0;
t.fs.prio = 1;
for (t.idx = 0; ; t.idx++) {
rc = doit(CHELSIO_T4_GET_FILTER, &t);
if (rc != 0 || t.idx == 0xffffffff)
break;
if (!header) {
printf("High Priority TCAM Region:\n");
do_show_info_header(mode);
header = 1;
hpfilter = 1;
}
do_show_one_filter_info(&t, mode);
}
}
header = 0;
bzero(&t, sizeof (t));
t.idx = 0;
t.fs.hash = hash;
for (t.idx = 0; ; t.idx++) {
@ -961,11 +983,13 @@ show_filters(int hash)
break;
if (!header) {
if (hpfilter)
printf("\nNormal Priority TCAM Region:\n");
do_show_info_header(mode);
header = 1;
}
do_show_one_filter_info(&t, mode);
};
}
return (rc);
}
@ -1092,10 +1116,11 @@ set_filter_mode(int argc, const char *argv[])
}
static int
del_filter(uint32_t idx, int hashfilter)
del_filter(uint32_t idx, int prio, int hashfilter)
{
struct t4_filter t;
t.fs.prio = prio;
t.fs.hash = hashfilter;
t.idx = idx;
@ -1225,6 +1250,15 @@ set_filter(uint32_t idx, int argc, const char *argv[], int hash)
} else if (!parse_val("hitcnts", args, &val)) {
t.fs.hitcnts = val;
} else if (!parse_val("prio", args, &val)) {
if (hash) {
warnx("Hashfilters doesn't support \"prio\"\n");
return (EINVAL);
}
if (val != 0 && val != 1) {
warnx("invalid priority \"%s\"; must be"
" \"0\" or \"1\"", argv[start_arg + 1]);
return (EINVAL);
}
t.fs.prio = val;
} else if (!parse_val("rpttid", args, &val)) {
t.fs.rpttid = 1;
@ -1406,10 +1440,33 @@ filter_cmd(int argc, const char *argv[], int hashfilter)
}
idx = (uint32_t) val;
/* <idx> delete|clear */
if (argc == 2 &&
/* <idx> delete|clear [prio 0|1] */
if ((argc == 2 || argc == 4) &&
(strcmp(argv[1], "delete") == 0 || strcmp(argv[1], "clear") == 0)) {
return del_filter(idx, hashfilter);
int prio = 0;
if (argc == 4) {
if (hashfilter) {
warnx("stray arguments after \"%s\".", argv[1]);
return (EINVAL);
}
if (strcmp(argv[2], "prio") != 0) {
warnx("\"prio\" is the only valid keyword "
"after \"%s\", found \"%s\" instead.",
argv[1], argv[2]);
return (EINVAL);
}
s = str_to_number(argv[3], NULL, &val);
if (*s || val < 0 || val > 1) {
warnx("%s \"%s\"; must be \"0\" or \"1\".",
argv[2], argv[3]);
return (EINVAL);
}
prio = (int)val;
}
return del_filter(idx, prio, hashfilter);
}
/* skip <idx> */
@ -3557,6 +3614,7 @@ main(int argc, const char *argv[])
}
nexus = argv[1];
chip_id = nexus[1] - '0';
/* progname and nexus */
argc -= 2;