1
/* Copyright (C) 2003,2004 Andi Kleen, SuSE Labs.
3
libnuma is free software; you can redistribute it and/or
4
modify it under the terms of the GNU Lesser General Public
5
License as published by the Free Software Foundation; version
8
libnuma is distributed in the hope that it will be useful,
9
but WITHOUT ANY WARRANTY; without even the implied warranty of
10
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11
Lesser General Public License for more details.
13
You should find a copy of v2.1 of the GNU Lesser General Public License
14
somewhere on your Linux system; if not, write to the Free Software
15
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
17
#include <sys/types.h>
18
#include <asm/unistd.h>
23
#define WEAK __attribute__((weak))
25
#if !defined(__NR_mbind) || !defined(__NR_set_mempolicy) || \
26
!defined(__NR_get_mempolicy)
28
#if defined(__x86_64__)
30
#define __NR_sched_setaffinity 203
31
#define __NR_sched_getaffinity 204
33
/* Official allocation */
35
#define __NR_mbind 237
36
#define __NR_set_mempolicy 238
37
#define __NR_get_mempolicy 239
39
#elif defined(__ia64__)
40
#define __NR_sched_setaffinity 1231
41
#define __NR_sched_getaffinity 1232
43
/* Official allocation */
45
#define __NR_mbind 1259
46
#define __NR_get_mempolicy 1260
47
#define __NR_set_mempolicy 1261
49
#elif defined(__i386__)
51
/* semi-official allocation (in -mm) */
53
#define __NR_mbind 274
54
#define __NR_get_mempolicy 275
55
#define __NR_set_mempolicy 276
57
#elif defined(__ppc64__) || defined(__ppc__)
59
#define __NR_mbind 259
60
#define __NR_get_mempolicy 260
61
#define __NR_set_mempolicy 261
64
#error "Add syscalls for your architecture or update kernel headers"
69
#if defined(__x86_64__)
70
/* 6 argument calls on x86-64 are often buggy in both glibc and
71
asm/unistd.h. Add a working version here. */
72
long syscall6(long call, long a, long b, long c, long d, long e, long f)
75
asm volatile ("movq %[d],%%r10 ; movq %[e],%%r8 ; movq %[f],%%r9 ; syscall"
77
: "0" (call),"D" (a),"S" (b), "d" (c),
78
[d] "g" (d), [e] "g" (e), [f] "g" (f) :
79
"r11","rcx","r8","r10","r9","memory" );
86
#elif defined(__i386__)
88
/* i386 has buggy syscall6 in glibc too. This is tricky to do
89
in inline assembly because it clobbers so many registers. Do it
97
" movl (0+5)*4(%esp),%eax\n"
98
" movl (1+5)*4(%esp),%ebx\n"
99
" movl (2+5)*4(%esp),%ecx\n"
100
" movl (3+5)*4(%esp),%edx\n"
101
" movl (4+5)*4(%esp),%esi\n"
102
" movl (5+5)*4(%esp),%edi\n"
103
" movl (6+5)*4(%esp),%ebp\n"
111
extern long __syscall6(long n, long a, long b, long c, long d, long e, long f);
113
long syscall6(long call, long a, long b, long c, long d, long e, long f)
115
long res = __syscall6(call,a,b,c,d,e,f);
124
#define syscall6 syscall
127
long WEAK get_mempolicy(int *policy,
128
unsigned long *nmask, unsigned long maxnode,
129
void *addr, int flags)
131
return syscall(__NR_get_mempolicy, policy, nmask, maxnode, addr, flags);
134
long WEAK mbind(void *start, unsigned long len, int mode,
135
unsigned long *nmask, unsigned long maxnode, unsigned flags)
137
return syscall6(__NR_mbind, (long)start, len, mode, (long)nmask, maxnode, flags);
140
long WEAK set_mempolicy(int mode, unsigned long *nmask,
141
unsigned long maxnode)
143
return syscall(__NR_set_mempolicy,mode,nmask,maxnode);
146
/* SLES8 glibc doesn't define those */
148
int numa_sched_setaffinity(pid_t pid, unsigned len, unsigned long *mask)
150
return syscall(__NR_sched_setaffinity,pid,len,mask);
153
int numa_sched_getaffinity(pid_t pid, unsigned len, unsigned long *mask)
155
return syscall(__NR_sched_getaffinity,pid,len,mask);
159
make_internal_alias(numa_sched_getaffinity);
160
make_internal_alias(numa_sched_setaffinity);
161
make_internal_alias(get_mempolicy);
162
make_internal_alias(set_mempolicy);
163
make_internal_alias(mbind);