aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--sys/kern/kern_cpuset.c22
-rw-r--r--sys/sys/cpuset.h1
-rw-r--r--sys/sys/smp.h1
-rw-r--r--sys/x86/acpica/srat.c3
-rw-r--r--usr.bin/cpuset/cpuset.111
-rw-r--r--usr.bin/cpuset/cpuset.c30
6 files changed, 49 insertions, 19 deletions
diff --git a/sys/kern/kern_cpuset.c b/sys/kern/kern_cpuset.c
index 49339db7a270..d18c89ee686d 100644
--- a/sys/kern/kern_cpuset.c
+++ b/sys/kern/kern_cpuset.c
@@ -56,6 +56,10 @@ __FBSDID("$FreeBSD$");
#include <sys/interrupt.h>
#include <vm/uma.h>
+#include <vm/vm.h>
+#include <vm/vm_page.h>
+#include <vm/vm_param.h>
+#include <vm/vm_phys.h>
#ifdef DDB
#include <ddb/ddb.h>
@@ -113,6 +117,7 @@ SYSCTL_INT(_kern_sched, OID_AUTO, cpusetsize, CTLFLAG_RD,
SYSCTL_NULL_INT_PTR, sizeof(cpuset_t), "sizeof(cpuset_t)");
cpuset_t *cpuset_root;
+cpuset_t cpuset_domain[MAXMEMDOM];
/*
* Acquire a reference to a cpuset, all pointers must be tracked with refs.
@@ -457,6 +462,7 @@ cpuset_which(cpuwhich_t which, id_t id, struct proc **pp, struct thread **tdp,
return (0);
}
case CPU_WHICH_IRQ:
+ case CPU_WHICH_DOMAIN:
return (0);
default:
return (EINVAL);
@@ -810,7 +816,8 @@ out:
/*
- * Creates the cpuset for thread0. We make two sets:
+ * Creates system-wide cpusets and the cpuset for thread0 including two
+ * sets:
*
* 0 - The root set which should represent all valid processors in the
* system. It is initially created with a mask of all processors
@@ -856,6 +863,10 @@ cpuset_thread0(void)
*/
cpuset_unr = new_unrhdr(2, INT_MAX, NULL);
+ /* MD Code is responsible for initializing sets if vm_ndomains > 1. */
+ if (vm_ndomains == 1)
+ CPU_COPY(&all_cpus, &cpuset_domain[0]);
+
return (set);
}
@@ -1010,6 +1021,7 @@ sys_cpuset_getid(struct thread *td, struct cpuset_getid_args *uap)
case CPU_WHICH_JAIL:
break;
case CPU_WHICH_IRQ:
+ case CPU_WHICH_DOMAIN:
return (EINVAL);
}
switch (uap->level) {
@@ -1073,6 +1085,7 @@ sys_cpuset_getaffinity(struct thread *td, struct cpuset_getaffinity_args *uap)
case CPU_WHICH_JAIL:
break;
case CPU_WHICH_IRQ:
+ case CPU_WHICH_DOMAIN:
error = EINVAL;
goto out;
}
@@ -1104,6 +1117,12 @@ sys_cpuset_getaffinity(struct thread *td, struct cpuset_getaffinity_args *uap)
case CPU_WHICH_IRQ:
error = intr_getaffinity(uap->id, mask);
break;
+ case CPU_WHICH_DOMAIN:
+ if (uap->id >= vm_ndomains)
+ error = ESRCH;
+ else
+ CPU_COPY(&cpuset_domain[uap->id], mask);
+ break;
}
break;
default:
@@ -1182,6 +1201,7 @@ sys_cpuset_setaffinity(struct thread *td, struct cpuset_setaffinity_args *uap)
case CPU_WHICH_JAIL:
break;
case CPU_WHICH_IRQ:
+ case CPU_WHICH_DOMAIN:
error = EINVAL;
goto out;
}
diff --git a/sys/sys/cpuset.h b/sys/sys/cpuset.h
index d8e7450ee43a..d3d60e773ec3 100644
--- a/sys/sys/cpuset.h
+++ b/sys/sys/cpuset.h
@@ -76,6 +76,7 @@
#define CPU_WHICH_CPUSET 3 /* Specifies a set id. */
#define CPU_WHICH_IRQ 4 /* Specifies an irq #. */
#define CPU_WHICH_JAIL 5 /* Specifies a jail id. */
+#define CPU_WHICH_DOMAIN 6 /* Specifies a NUMA domain id. */
/*
* Reserved cpuset identifiers.
diff --git a/sys/sys/smp.h b/sys/sys/smp.h
index 42cb8df058ce..58b1754c0409 100644
--- a/sys/sys/smp.h
+++ b/sys/sys/smp.h
@@ -85,6 +85,7 @@ extern int mp_ncpus;
extern volatile int smp_started;
extern cpuset_t all_cpus;
+extern cpuset_t cpuset_domain[MAXMEMDOM]; /* CPUs in each NUMA domain. */
/*
* Macro allowing us to determine whether a CPU is absent at any given
diff --git a/sys/x86/acpica/srat.c b/sys/x86/acpica/srat.c
index c4d205b3c3dd..8335a8c0c084 100644
--- a/sys/x86/acpica/srat.c
+++ b/sys/x86/acpica/srat.c
@@ -342,7 +342,7 @@ srat_walk_table(acpi_subtable_handler *handler, void *arg)
}
/*
- * Setup per-CPU ACPI IDs.
+ * Setup per-CPU domain IDs.
*/
static void
srat_set_cpus(void *dummy)
@@ -363,6 +363,7 @@ srat_set_cpus(void *dummy)
panic("SRAT: CPU with APIC ID %u is not known",
pc->pc_apic_id);
pc->pc_domain = cpu->domain;
+ CPU_SET(i, &cpuset_domain[cpu->domain]);
if (bootverbose)
printf("SRAT: CPU %u has memory domain %d\n", i,
cpu->domain);
diff --git a/usr.bin/cpuset/cpuset.1 b/usr.bin/cpuset/cpuset.1
index 8ea2702499f1..ac11b4c2fbfe 100644
--- a/usr.bin/cpuset/cpuset.1
+++ b/usr.bin/cpuset/cpuset.1
@@ -46,12 +46,13 @@
.Fl C
.Fl p Ar pid
.Nm
-.Op Fl cr
+.Op Fl c
.Op Fl l Ar cpu-list
.Op Fl j Ar jailid | Fl p Ar pid | Fl t Ar tid | Fl s Ar setid | Fl x Ar irq
.Nm
-.Op Fl cgir
-.Op Fl j Ar jailid | Fl p Ar pid | Fl t Ar tid | Fl s Ar setid | Fl x Ar irq
+.Fl g
+.Op Fl cir
+.Op Fl d Ar domain | j Ar jailid | Fl p Ar pid | Fl t Ar tid | Fl s Ar setid | Fl x Ar irq
.Sh DESCRIPTION
The
.Nm
@@ -62,7 +63,7 @@ about processor binding, sets, and available processors in the system.
.Nm
requires a target to modify or query.
The target may be specified as a command, process id, thread id, a
-cpuset id, an irq or a jail id.
+cpuset id, an irq, a jail id, or a NUMA domain.
Using
.Fl g
the target's set id or mask may be queried.
@@ -108,6 +109,8 @@ Create a new cpuset and assign the target process to that set.
.It Fl c
The requested operation should reference the cpuset available via the
target specifier.
+.It Fl d Ar domain
+Specifies a NUMA domain id as the target of the operation.
.It Fl g
Causes
.Nm
diff --git a/usr.bin/cpuset/cpuset.c b/usr.bin/cpuset/cpuset.c
index 898c3e5ed8ee..c619259c306e 100644
--- a/usr.bin/cpuset/cpuset.c
+++ b/usr.bin/cpuset/cpuset.c
@@ -48,6 +48,7 @@ __FBSDID("$FreeBSD$");
static int Cflag;
static int cflag;
+static int dflag;
static int gflag;
static int iflag;
static int jflag;
@@ -161,7 +162,8 @@ printset(cpuset_t *mask)
printf("\n");
}
-static const char *whichnames[] = { NULL, "tid", "pid", "cpuset", "irq", "jail" };
+static const char *whichnames[] = { NULL, "tid", "pid", "cpuset", "irq", "jail",
+ "domain" };
static const char *levelnames[] = { NULL, " root", " cpuset", "" };
static void
@@ -206,17 +208,20 @@ main(int argc, char *argv[])
level = CPU_LEVEL_WHICH;
which = CPU_WHICH_PID;
id = pid = tid = setid = -1;
- while ((ch = getopt(argc, argv, "Ccgij:l:p:rs:t:x:")) != -1) {
+ while ((ch = getopt(argc, argv, "Ccd:gij:l:p:rs:t:x:")) != -1) {
switch (ch) {
case 'C':
Cflag = 1;
break;
case 'c':
- if (rflag)
- usage();
cflag = 1;
level = CPU_LEVEL_CPUSET;
break;
+ case 'd':
+ dflag = 1;
+ which = CPU_WHICH_DOMAIN;
+ id = atoi(optarg);
+ break;
case 'g':
gflag = 1;
break;
@@ -238,8 +243,6 @@ main(int argc, char *argv[])
id = pid = atoi(optarg);
break;
case 'r':
- if (cflag)
- usage();
level = CPU_LEVEL_ROOT;
rflag = 1;
break;
@@ -268,7 +271,7 @@ main(int argc, char *argv[])
if (argc || Cflag || lflag)
usage();
/* Only one identity specifier. */
- if (jflag + xflag + sflag + pflag + tflag > 1)
+ if (dflag + jflag + xflag + sflag + pflag + tflag > 1)
usage();
if (iflag)
printsetid();
@@ -276,13 +279,13 @@ main(int argc, char *argv[])
printaffinity();
exit(EXIT_SUCCESS);
}
- if (iflag)
+ if (dflag || iflag || rflag)
usage();
/*
* The user wants to run a command with a set and possibly cpumask.
*/
if (argc) {
- if (Cflag | pflag | rflag | tflag | xflag | jflag)
+ if (Cflag || pflag || tflag || xflag || jflag)
usage();
if (sflag) {
if (cpuset_setid(CPU_WHICH_PID, -1, setid))
@@ -303,9 +306,9 @@ main(int argc, char *argv[])
/*
* We're modifying something that presently exists.
*/
- if (Cflag && (sflag || rflag || !pflag || tflag || xflag || jflag))
+ if (Cflag && (jflag || !pflag || sflag || tflag || xflag))
usage();
- if (!lflag && (cflag || rflag))
+ if (!lflag && cflag)
usage();
if (!lflag && !(Cflag || sflag))
usage();
@@ -354,8 +357,9 @@ usage(void)
fprintf(stderr,
" cpuset [-c] [-l cpu-list] -C -p pid\n");
fprintf(stderr,
- " cpuset [-cr] [-l cpu-list] [-j jailid | -p pid | -t tid | -s setid | -x irq]\n");
+ " cpuset [-c] [-l cpu-list] [-j jailid | -p pid | -t tid | -s setid | -x irq]\n");
fprintf(stderr,
- " cpuset [-cgir] [-j jailid | -p pid | -t tid | -s setid | -x irq]\n");
+ " cpuset -g [-cir] [-d domain | -j jailid | -p pid | -t tid | -s setid |\n"
+ " -x irq]\n");
exit(1);
}