This is the mail archive of the
libc-alpha@sourceware.org
mailing list for the glibc project.
Re: What *is* the API for sched_getaffinity? Should sched_getaffinity always succeed when using cpu_set_t?
- From: Rich Felker <dalias at aerifal dot cx>
- To: KOSAKI Motohiro <kosaki dot motohiro at gmail dot com>
- Cc: libc-alpha <libc-alpha at sourceware dot org>
- Date: Tue, 16 Jul 2013 09:47:00 -0400
- Subject: Re: What *is* the API for sched_getaffinity? Should sched_getaffinity always succeed when using cpu_set_t?
- References: <51E42BFE dot 7000301 at redhat dot com> <51E4A0BB dot 2070802 at gmail dot com> <51E4A123 dot 9070001 at gmail dot com>
On Mon, Jul 15, 2013 at 09:25:55PM -0400, KOSAKI Motohiro wrote:
> (7/15/13 9:24 PM), KOSAKI Motohiro wrote:
> >Hi
> >
> >>There are 3 ways to determine the correct size of the possible
> >>cpu mask size:
> >>
> >>(a) Read it from sysfs /sys/devices/system/cpu/online, which
> >>has the actual number of possibly online cpus.
> >>
> >>(b) Interpret /proc/cpuinfo or /proc/stat.
> >>
> >>(c) Call the kernel syscall sched_getaffinity with increasingly
> >>larger values for cpusetsize in an attempt to manually
> >>determine the cpu mask size.
> >>
> >>Methods (a) and (b) are already used by sysconf(_SC_PROCESSORS_ONLN)
> >>to determine the value to return.
> >
> >Nit.
> >
> >sysconf(_SC_NPROCESSORS_ONLN) returns number of online cpus. not possible cpus.
> >
> >online cpus: number of _now_ onlined cpus
> >possible cpus: number of maximum cpus on the system. (i.e. depend on arch and
> >firmware and ACPI table)
> >
> >/sys/devices/system/cpu/possible returns possible cpu mask. AFAIK, unfortunately,
> >sysconf() doesn't support to get possible cpus.
>
> I meant, _SC_NPROCESSORS_ONLN is racy and not recommended if cpu hotplug is happen.
This race makes me think having sched_getaffinity always succeed may
be a bad idea; there's no way to work around the race. What if it only
succeeded when the current number of cpus online (as opposed to the
kernel limit) is smaller than the cpuset? glibc could work around old
kernels that fail in the latter case by, in the EINVAL failure path,
trying again to get the whole cpuset to its own buffer and then
copying that back to the caller's buffer if it fits.
Rich