affinity_linux.go (1927B)
1 // Copyright 2018 The Go Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 // CPU affinity functions 6 7 package unix 8 9 import ( 10 "math/bits" 11 "unsafe" 12 ) 13 14 const cpuSetSize = _CPU_SETSIZE / _NCPUBITS 15 16 // CPUSet represents a CPU affinity mask. 17 type CPUSet [cpuSetSize]cpuMask 18 19 func schedAffinity(trap uintptr, pid int, set *CPUSet) error { 20 _, _, e := RawSyscall(trap, uintptr(pid), uintptr(unsafe.Sizeof(*set)), uintptr(unsafe.Pointer(set))) 21 if e != 0 { 22 return errnoErr(e) 23 } 24 return nil 25 } 26 27 // SchedGetaffinity gets the CPU affinity mask of the thread specified by pid. 28 // If pid is 0 the calling thread is used. 29 func SchedGetaffinity(pid int, set *CPUSet) error { 30 return schedAffinity(SYS_SCHED_GETAFFINITY, pid, set) 31 } 32 33 // SchedSetaffinity sets the CPU affinity mask of the thread specified by pid. 34 // If pid is 0 the calling thread is used. 35 func SchedSetaffinity(pid int, set *CPUSet) error { 36 return schedAffinity(SYS_SCHED_SETAFFINITY, pid, set) 37 } 38 39 // Zero clears the set s, so that it contains no CPUs. 40 func (s *CPUSet) Zero() { 41 for i := range s { 42 s[i] = 0 43 } 44 } 45 46 func cpuBitsIndex(cpu int) int { 47 return cpu / _NCPUBITS 48 } 49 50 func cpuBitsMask(cpu int) cpuMask { 51 return cpuMask(1 << (uint(cpu) % _NCPUBITS)) 52 } 53 54 // Set adds cpu to the set s. 55 func (s *CPUSet) Set(cpu int) { 56 i := cpuBitsIndex(cpu) 57 if i < len(s) { 58 s[i] |= cpuBitsMask(cpu) 59 } 60 } 61 62 // Clear removes cpu from the set s. 63 func (s *CPUSet) Clear(cpu int) { 64 i := cpuBitsIndex(cpu) 65 if i < len(s) { 66 s[i] &^= cpuBitsMask(cpu) 67 } 68 } 69 70 // IsSet reports whether cpu is in the set s. 71 func (s *CPUSet) IsSet(cpu int) bool { 72 i := cpuBitsIndex(cpu) 73 if i < len(s) { 74 return s[i]&cpuBitsMask(cpu) != 0 75 } 76 return false 77 } 78 79 // Count returns the number of CPUs in the set s. 80 func (s *CPUSet) Count() int { 81 c := 0 82 for _, b := range s { 83 c += bits.OnesCount64(uint64(b)) 84 } 85 return c 86 }