From: Sepherosa Ziehau Date: Sun, 15 Jan 2017 08:53:39 +0000 (+0800) Subject: pthread: Implement pthread_attr_{get,set}affinity_np X-Git-Tag: v4.8.0rc~210 X-Git-Url: https://gitweb.dragonflybsd.org/dragonfly.git/commitdiff_plain/3ae362f2fd40a49b17fda7454bd8c25ca54f9902 pthread: Implement pthread_attr_{get,set}affinity_np --- diff --git a/include/pthread_np.h b/include/pthread_np.h index d6753a5e39..354d2115b6 100644 --- a/include/pthread_np.h +++ b/include/pthread_np.h @@ -42,8 +42,10 @@ typedef void (*pthread_switch_routine_t)(pthread_t, pthread_t); * Non-POSIX thread function prototype definitions: */ __BEGIN_DECLS -int pthread_attr_setcreatesuspend_np(pthread_attr_t *); int pthread_attr_get_np(pthread_t, pthread_attr_t *); +int pthread_attr_getaffinity_np(const pthread_attr_t *, size_t, cpu_set_t *); +int pthread_attr_setaffinity_np(pthread_attr_t *, size_t, const cpu_set_t *); +int pthread_attr_setcreatesuspend_np(pthread_attr_t *); int pthread_getaffinity_np(pthread_t, size_t, cpu_set_t *); int pthread_main_np(void); int pthread_multi_np(void); diff --git a/lib/libc/gen/Symbol.map b/lib/libc/gen/Symbol.map index dff18d24ab..7b2cddedc0 100644 --- a/lib/libc/gen/Symbol.map +++ b/lib/libc/gen/Symbol.map @@ -26,6 +26,7 @@ DF404.0 { pthread_atfork; pthread_attr_destroy; pthread_attr_get_np; + pthread_attr_getaffinity_np; pthread_attr_getdetachstate; pthread_attr_getguardsize; pthread_attr_getinheritsched; @@ -36,6 +37,7 @@ DF404.0 { pthread_attr_getstackaddr; pthread_attr_getstacksize; pthread_attr_init; + pthread_attr_setaffinity_np; pthread_attr_setcreatesuspend_np; pthread_attr_setdetachstate; pthread_attr_setguardsize; @@ -462,6 +464,7 @@ DFprivate_1.0 { _pthread_atfork; _pthread_attr_destroy; _pthread_attr_get_np; + _pthread_attr_getaffinity_np; _pthread_attr_getdetachstate; _pthread_attr_getguardsize; _pthread_attr_getinheritsched; @@ -472,6 +475,7 @@ DFprivate_1.0 { _pthread_attr_getstackaddr; _pthread_attr_getstacksize; _pthread_attr_init; + _pthread_attr_setaffinity_np; _pthread_attr_setcreatesuspend_np; _pthread_attr_setdetachstate; _pthread_attr_setguardsize; diff --git a/lib/libc/gen/_pthread_stubs.c b/lib/libc/gen/_pthread_stubs.c index dd3e603b4a..28a656462a 100644 --- a/lib/libc/gen/_pthread_stubs.c +++ b/lib/libc/gen/_pthread_stubs.c @@ -50,6 +50,7 @@ WR(__atfork, pthread_atfork); WR(stub_zero, pthread_attr_destroy); WR(stub_zero, pthread_attr_get_np); +WR(stub_zero, pthread_attr_getaffinity_np); WR(stub_zero, pthread_attr_getdetachstate); WR(stub_zero, pthread_attr_getguardsize); WR(stub_zero, pthread_attr_getinheritsched); @@ -60,6 +61,7 @@ WR(stub_zero, pthread_attr_getstack); WR(stub_zero, pthread_attr_getstackaddr); WR(stub_zero, pthread_attr_getstacksize); WR(stub_zero, pthread_attr_init); +WR(stub_zero, pthread_attr_setaffinity_np); WR(stub_zero, pthread_attr_setcreatesuspend_np); WR(stub_zero, pthread_attr_setdetachstate); WR(stub_zero, pthread_attr_setguardsize); diff --git a/lib/libc/include/namespace.h b/lib/libc/include/namespace.h index 0c51d1a094..a0f8ce9928 100644 --- a/lib/libc/include/namespace.h +++ b/lib/libc/include/namespace.h @@ -78,6 +78,7 @@ #define pthread_atfork _pthread_atfork #define pthread_attr_destroy _pthread_attr_destroy #define pthread_attr_get_np _pthread_attr_get_np +#define pthread_attr_getaffinity_np _pthread_attr_getaffinity_np #define pthread_attr_getdetachstate _pthread_attr_getdetachstate #define pthread_attr_getguardsize _pthread_attr_getguardsize #define pthread_attr_getinheritsched _pthread_attr_getinheritsched @@ -88,6 +89,7 @@ #define pthread_attr_getstackaddr _pthread_attr_getstackaddr #define pthread_attr_getstacksize _pthread_attr_getstacksize #define pthread_attr_init _pthread_attr_init +#define pthread_attr_setaffinity_np _pthread_attr_setaffinity_np #define pthread_attr_setcreatesuspend_np _pthread_attr_setcreatesuspend_np #define pthread_attr_setdetachstate _pthread_attr_setdetachstate #define pthread_attr_setguardsize _pthread_attr_setguardsize diff --git a/lib/libc/include/un-namespace.h b/lib/libc/include/un-namespace.h index 881c30b96a..17989e4385 100644 --- a/lib/libc/include/un-namespace.h +++ b/lib/libc/include/un-namespace.h @@ -59,6 +59,7 @@ #undef pthread_atfork #undef pthread_attr_destroy #undef pthread_attr_get_np +#undef pthread_attr_getaffinity_np #undef pthread_attr_getdetachstate #undef pthread_attr_getguardsize #undef pthread_attr_getinheritsched @@ -69,6 +70,7 @@ #undef pthread_attr_getstackaddr #undef pthread_attr_getstacksize #undef pthread_attr_init +#undef pthread_attr_setaffinity_np #undef pthread_attr_setcreatesuspend_np #undef pthread_attr_setdetachstate #undef pthread_attr_setguardsize diff --git a/lib/libc_r/uthread/Makefile.inc b/lib/libc_r/uthread/Makefile.inc index 200921c9e3..5d2693e2fd 100644 --- a/lib/libc_r/uthread/Makefile.inc +++ b/lib/libc_r/uthread/Makefile.inc @@ -12,6 +12,7 @@ SRCS+= \ uthread_attr_destroy.c \ uthread_attr_get_np.c \ uthread_attr_init.c \ + uthread_attr_getaffinity_np.c \ uthread_attr_getdetachstate.c \ uthread_attr_getinheritsched.c \ uthread_attr_getschedparam.c \ @@ -20,6 +21,7 @@ SRCS+= \ uthread_attr_getstack.c \ uthread_attr_getstackaddr.c \ uthread_attr_getstacksize.c \ + uthread_attr_setaffinity_np.c \ uthread_attr_setcreatesuspend_np.c \ uthread_attr_setdetachstate.c \ uthread_attr_setinheritsched.c \ diff --git a/include/pthread_np.h b/lib/libc_r/uthread/uthread_attr_getaffinity_np.c similarity index 50% copy from include/pthread_np.h copy to lib/libc_r/uthread/uthread_attr_getaffinity_np.c index d6753a5e39..7352c6f577 100644 --- a/include/pthread_np.h +++ b/lib/libc_r/uthread/uthread_attr_getaffinity_np.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996-98 John Birrell . + * Copyright (c) 1995 John Birrell . * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -10,14 +10,17 @@ * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the author nor the names of any co-contributors + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by John Birrell. + * 4. Neither the name of the author nor the names of any co-contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY JOHN BIRRELL AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) @@ -25,40 +28,34 @@ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. - * - * $FreeBSD: src/include/pthread_np.h,v 1.7.2.4 2003/01/10 15:41:17 fjoe Exp $ */ -#ifndef _PTHREAD_NP_H_ -#define _PTHREAD_NP_H_ -#include +#include +#include -/* - * Non-POSIX type definitions: - */ -typedef void (*pthread_switch_routine_t)(pthread_t, pthread_t); +#include +#include +#include +#include +#include "pthread_private.h" -/* - * Non-POSIX thread function prototype definitions: - */ -__BEGIN_DECLS -int pthread_attr_setcreatesuspend_np(pthread_attr_t *); -int pthread_attr_get_np(pthread_t, pthread_attr_t *); -int pthread_getaffinity_np(pthread_t, size_t, cpu_set_t *); -int pthread_main_np(void); -int pthread_multi_np(void); -int pthread_mutexattr_getkind_np(pthread_mutexattr_t); -int pthread_mutexattr_setkind_np(pthread_mutexattr_t *, int); -void pthread_resume_all_np(void); -int pthread_resume_np(pthread_t); -void pthread_set_name_np(pthread_t, const char *); -int pthread_setaffinity_np(pthread_t, size_t, const cpu_set_t *); -int pthread_single_np(void); -void pthread_suspend_all_np(void); -int pthread_suspend_np(pthread_t); -int pthread_switch_add_np(pthread_switch_routine_t); -int pthread_switch_delete_np(pthread_switch_routine_t); -int pthread_timedjoin_np(pthread_t, void **, const struct timespec *); -__END_DECLS +int +_pthread_attr_getaffinity_np(const pthread_attr_t *attr __unused, + size_t cpusetsize, cpu_set_t *mask) +{ + cpu_set_t mask1; + size_t len; + + len = sizeof(mask1); + if (sysctlbyname("machdep.smp_active", &mask1, &len, NULL, 0) < 0) + return (errno); -#endif + if (cpusetsize > sizeof(mask1)) { + memset(mask, 0, cpusetsize); + memcpy(mask, &mask1, sizeof(mask1)); + } else { + memcpy(mask, &mask1, cpusetsize); + } + return (0); +} +__strong_reference(_pthread_attr_getaffinity_np, pthread_attr_getaffinity_np); diff --git a/include/pthread_np.h b/lib/libc_r/uthread/uthread_attr_setaffinity_np.c similarity index 50% copy from include/pthread_np.h copy to lib/libc_r/uthread/uthread_attr_setaffinity_np.c index d6753a5e39..d46e4f2cc3 100644 --- a/include/pthread_np.h +++ b/lib/libc_r/uthread/uthread_attr_setaffinity_np.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996-98 John Birrell . + * Copyright (c) 1995 John Birrell . * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -10,14 +10,17 @@ * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the author nor the names of any co-contributors + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by John Birrell. + * 4. Neither the name of the author nor the names of any co-contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY JOHN BIRRELL AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) @@ -25,40 +28,18 @@ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. - * - * $FreeBSD: src/include/pthread_np.h,v 1.7.2.4 2003/01/10 15:41:17 fjoe Exp $ */ -#ifndef _PTHREAD_NP_H_ -#define _PTHREAD_NP_H_ - -#include -/* - * Non-POSIX type definitions: - */ -typedef void (*pthread_switch_routine_t)(pthread_t, pthread_t); +#include +#include +#include +#include "pthread_private.h" -/* - * Non-POSIX thread function prototype definitions: - */ -__BEGIN_DECLS -int pthread_attr_setcreatesuspend_np(pthread_attr_t *); -int pthread_attr_get_np(pthread_t, pthread_attr_t *); -int pthread_getaffinity_np(pthread_t, size_t, cpu_set_t *); -int pthread_main_np(void); -int pthread_multi_np(void); -int pthread_mutexattr_getkind_np(pthread_mutexattr_t); -int pthread_mutexattr_setkind_np(pthread_mutexattr_t *, int); -void pthread_resume_all_np(void); -int pthread_resume_np(pthread_t); -void pthread_set_name_np(pthread_t, const char *); -int pthread_setaffinity_np(pthread_t, size_t, const cpu_set_t *); -int pthread_single_np(void); -void pthread_suspend_all_np(void); -int pthread_suspend_np(pthread_t); -int pthread_switch_add_np(pthread_switch_routine_t); -int pthread_switch_delete_np(pthread_switch_routine_t); -int pthread_timedjoin_np(pthread_t, void **, const struct timespec *); -__END_DECLS +int +_pthread_attr_setaffinity_np(pthread_attr_t *attr __unused, + size_t cpusetsize __unused, const cpu_set_t *mask __unused) +{ -#endif + return (EOPNOTSUPP); +} +__strong_reference(_pthread_attr_setaffinity_np, pthread_attr_setaffinity_np); diff --git a/lib/libpthread/Makefile b/lib/libpthread/Makefile index 88a75e8b74..924822b9ae 100644 --- a/lib/libpthread/Makefile +++ b/lib/libpthread/Makefile @@ -10,6 +10,7 @@ MAN+= \ pthread_atfork.3 \ pthread_attr.3 \ pthread_attr_get_np.3 \ + pthread_attr_setaffinity_np.3 \ pthread_attr_setcreatesuspend_np.3 \ pthread_barrier_destroy.3 \ pthread_barrierattr.3 \ @@ -100,6 +101,7 @@ MLINKS+= \ pthread_attr.3 pthread_attr_setstack.3 \ pthread_attr.3 pthread_attr_setstackaddr.3 \ pthread_attr.3 pthread_attr_setstacksize.3 \ + pthread_attr_setaffinity_np.3 pthread_attr_getaffinity_np.3 \ pthread_barrierattr.3 pthread_barrierattr_destroy.3 \ pthread_barrierattr.3 pthread_barrierattr_getpshared.3 \ pthread_barrierattr.3 pthread_barrierattr_init.3 \ diff --git a/lib/libpthread/pthread_attr_setaffinity_np.3 b/lib/libpthread/pthread_attr_setaffinity_np.3 new file mode 100644 index 0000000000..1567faac82 --- /dev/null +++ b/lib/libpthread/pthread_attr_setaffinity_np.3 @@ -0,0 +1,113 @@ +.\" Copyright (c) 2017 The DragonFly Project. All rights reserved. +.\" +.\" This code is derived from software contributed to The DragonFly Project +.\" by Sepherosa Ziehau . +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in +.\" the documentation and/or other materials provided with the +.\" distribution. +.\" 3. Neither the name of The DragonFly Project nor the names of its +.\" contributors may be used to endorse or promote products derived +.\" from this software without specific, prior written permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +.\" ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +.\" LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS +.\" FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE +.\" COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, +.\" INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING, +.\" BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +.\" LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED +.\" AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +.\" OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT +.\" OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.Dd January 15, 2017 +.Dt PTHREAD_ATTR_SETAFFINITY_NP 2 +.Os +.Sh NAME +.Nm pthread_attr_setaffinity_np, +.Nm pthread_attr_getaffinity_np +.Nd set and get the thread's CPU affinity mask attribute +.Sh LIBRARY +.Lb libpthread +.Sh SYNOPSIS +.In pthread.h +.In pthread_np.h +.Ft int +.Fn pthread_attr_setaffinity_np "pthread_attr_t *attr" "size_t cpusetsize" "const cpu_set_t *mask" +.Ft int +.Fn pthread_attr_getaffinity_np "const pthread_attr_t *attr" "size_t cpusetsize" "cpu_set_t *mask" +.Sh DESCRIPTION +.Pp +The +.Fn pthread_attr_setaffinity_np +sets the CPU affinity mask of the +.Fa attr +to the value specified by the +.Fa mask . +The +.Fa cpusetsize +is the length (in bytes) of the data pointed to by +.Fa mask . +Normally this argument would be specified as sizeof(cpu_set_t). +The threads created by +.Xr pthread_create 2 +with the +.Fa attr +will use the CPU affinity mask of the +.Fa attr . +.Pp +.Fn pthread_attr_getaffinity_np +writes the CPU affinity mask of the +.Fa attr +to the cpu_set_t structure pointed to by +.Fa mask . +.Pp +The cpu_set_t data structure represents a set of CPUs. +See +.Xr sched_setaffinity 2 +for details. +.Sh RETURN VALUES +If successful, +these functions will return zero. +Otherwise an error number will be returned to indicate the error. +.Sh ERRORS +The +.Fn pthread_attr_setaffinity_np +and +.Fn pthread_attr_getaffinity_np +will fail if: +.Bl -tag -width Er +.It Bq Er EFAULT +The +.Fa mask +parameter is outside the process's allocated address space. +.It Bq Er EINVAL +The +.Fa attr +parameter is invalid. +.It Bq Er EPERM +The +.Fa mask +does not contain a valid CPU. +.El +.Sh SEE ALSO +.Xr pthread_create 3 +.Xr pthread_getaffinity_np 2 +.Xr pthread_setaffinity_np 2 +.Sh HISTORY +The +.Fn pthread_attr_setaffinity_np +and +.Fn pthread_attr_getaffinity_np +functions first appeared in +.Dx 4.7 . diff --git a/lib/libthread_xu/pthread.map b/lib/libthread_xu/pthread.map index 71f0720cc9..4b1bfe7a14 100644 --- a/lib/libthread_xu/pthread.map +++ b/lib/libthread_xu/pthread.map @@ -47,6 +47,7 @@ global: _pthread_attr_default; _pthread_attr_destroy; _pthread_attr_get_np; + _pthread_attr_getaffinity_np; _pthread_attr_getdetachstate; _pthread_attr_getguardsize; _pthread_attr_getinheritsched; @@ -57,6 +58,7 @@ global: _pthread_attr_getstackaddr; _pthread_attr_getstacksize; _pthread_attr_init; + _pthread_attr_setaffinity_np; _pthread_attr_setcreatesuspend_np; _pthread_attr_setdetachstate; _pthread_attr_setguardsize; @@ -209,6 +211,7 @@ global: pthread_barrierattr_setpshared; pthread_attr_destroy; pthread_attr_get_np; + pthread_attr_getaffinity_np; pthread_attr_getdetachstate; pthread_attr_getguardsize; pthread_attr_getinheritsched; @@ -219,6 +222,7 @@ global: pthread_attr_getstackaddr; pthread_attr_getstacksize; pthread_attr_init; + pthread_attr_setaffinity_np; pthread_attr_setcreatesuspend_np; pthread_attr_setdetachstate; pthread_attr_setguardsize; diff --git a/lib/libthread_xu/thread/thr_attr.c b/lib/libthread_xu/thread/thr_attr.c index 8916c7218b..2db3f6f1e3 100644 --- a/lib/libthread_xu/thread/thr_attr.c +++ b/lib/libthread_xu/thread/thr_attr.c @@ -32,6 +32,8 @@ */ #include "namespace.h" +#include +#include #include #include #include @@ -91,6 +93,39 @@ _pthread_attr_get_np(pthread_t pid, pthread_attr_t *dst) __strong_reference(_pthread_attr_get_np, pthread_attr_get_np); +int +_pthread_attr_getaffinity_np(const pthread_attr_t *attr, size_t cpusetsize, + cpu_set_t *mask) +{ + const cpu_set_t *ret; + cpu_set_t mask1; + + if (attr == NULL || *attr == NULL || mask == NULL) + return (EINVAL); + + if (((*attr)->flags & THR_CPUMASK) == 0) { + size_t len; + + len = sizeof(mask1); + if (sysctlbyname("machdep.smp_active", &mask1, &len, + NULL, 0) < 0) + return (errno); + ret = &mask1; + } else { + ret = &(*attr)->cpumask; + } + + if (cpusetsize > sizeof(*ret)) { + memset(mask, 0, cpusetsize); + memcpy(mask, ret, sizeof(*ret)); + } else { + memcpy(mask, ret, cpusetsize); + } + return (0); +} + +__strong_reference(_pthread_attr_getaffinity_np, pthread_attr_getaffinity_np); + int _pthread_attr_getdetachstate(const pthread_attr_t *attr, int *detachstate) { @@ -277,6 +312,36 @@ _pthread_attr_init(pthread_attr_t *attr) __strong_reference(_pthread_attr_init, pthread_attr_init); +int +_pthread_attr_setaffinity_np(pthread_attr_t *attr, size_t cpusetsize, + const cpu_set_t *mask) +{ + cpu_set_t active, mask1; + size_t len, cplen = cpusetsize; + + if (attr == NULL || *attr == NULL || mask == NULL) + return (EINVAL); + + if (cplen > sizeof(mask1)) + cplen = sizeof(mask1); + CPU_ZERO(&mask1); + memcpy(&mask1, mask, cplen); + + len = sizeof(active); + if (sysctlbyname("machdep.smp_active", &active, &len, NULL, 0) < 0) + return (errno); + + CPUMASK_ANDMASK(mask1, active); + if (CPUMASK_TESTZERO(mask1)) + return (EPERM); + + (*attr)->cpumask = mask1; + (*attr)->flags |= THR_CPUMASK; + return (0); +} + +__strong_reference(_pthread_attr_setaffinity_np, pthread_attr_setaffinity_np); + int _pthread_attr_setcreatesuspend_np(pthread_attr_t *attr) { diff --git a/lib/libthread_xu/thread/thr_create.c b/lib/libthread_xu/thread/thr_create.c index 75ca76c4a7..9148a956dd 100644 --- a/lib/libthread_xu/thread/thr_create.c +++ b/lib/libthread_xu/thread/thr_create.c @@ -54,6 +54,7 @@ _pthread_create(pthread_t * thread, const pthread_attr_t * attr, void *stack; sigset_t sigmask, oldsigmask; struct pthread *curthread, *new_thread; + const cpu_set_t *cpumask = NULL; int ret = 0, locked; _thr_check_init(); @@ -85,6 +86,8 @@ _pthread_create(pthread_t * thread, const pthread_attr_t * attr, * inherited in following code. */ } + if (new_thread->attr.flags & THR_CPUMASK) + cpumask = &new_thread->attr.cpumask; if (create_stack(&new_thread->attr) != 0) { /* Insufficient memory to create a stack: */ @@ -165,7 +168,7 @@ _pthread_create(pthread_t * thread, const pthread_attr_t * attr, SIGFILLSET(sigmask); __sys_sigprocmask(SIG_SETMASK, &sigmask, &oldsigmask); new_thread->sigmask = oldsigmask; - ret = lwp_create(&create_params); + ret = lwp_create2(&create_params, cpumask); __sys_sigprocmask(SIG_SETMASK, &oldsigmask, NULL); if (ret != 0) { if (!locked) diff --git a/lib/libthread_xu/thread/thr_private.h b/lib/libthread_xu/thread/thr_private.h index 9b8bf57e63..7fc1ae54d2 100644 --- a/lib/libthread_xu/thread/thr_private.h +++ b/lib/libthread_xu/thread/thr_private.h @@ -44,6 +44,7 @@ #include #include #include +#include #include #include #include @@ -237,10 +238,12 @@ struct pthread_attr { int prio; int suspend; #define THR_STACK_USER 0x100 /* 0xFF reserved for */ +#define THR_CPUMASK 0x200 /* cpumask is valid */ int flags; void *stackaddr_attr; size_t stacksize_attr; size_t guardsize_attr; + cpumask_t cpumask; }; /* diff --git a/sys/sys/param.h b/sys/sys/param.h index c0725ba597..83dc571f4b 100644 --- a/sys/sys/param.h +++ b/sys/sys/param.h @@ -143,6 +143,7 @@ * 400706 - sched_{set,get}affinity() * 400707 - pthread_{set,get}affinity_np() * 400708 - lwp_create2() + * 400709 - pthread_attr_{set,get}affinity_np() */ #undef __DragonFly_version #define __DragonFly_version 400708 /* propagated to newvers */