SlideShare ist ein Scribd-Unternehmen logo
1 von 7
Downloaden Sie, um offline zu lesen
CPU Affinity
Bind specific processes to specific processors with a new system call.

The ability in Linux to bind one or more processes to one or more processors, called CPU
affinity, is a long-requested feature. The idea is to say ³always run this process on processor one´
or ³run these processes on all processors but processor zero´. The scheduler then obeys the
order, and the process runs only on the allowed processors.

Other operating systems, such as Windows NT, have long provided a system call to set the CPU
affinity for a process. Consequently, demand for such a system call in Linux has been high.
Finally, the 2.5 kernel introduced a set of system calls for setting and retrieving the CPU affinity
of a process.

In this article, I look at the reasons for introducing a CPU affinity interface to Linux. I then cover
how to use the interface in your programs. If you are not a programmer or if you have an existing
program you are unable to modify, I cover a simple utility for changing the affinity of a given
process using its PID. Finally, we look at the actual implementation of the system call.

Soft vs. Hard CPU Affinity

There are two types of CPU affinity. The first, soft affinity, also called natural affinity, is the
tendency of a scheduler to try to keep processes on the same CPU as long as possible. It is
merely an attempt; if it is ever infeasible, the processes certainly will migrate to another
processor. The new O(1) scheduler in 2.5 exhibits excellent natural affinity. On the opposite end,
however, is the 2.4 scheduler, which has poor CPU affinity. This behavior results in the ping-
pong effect. The scheduler bounces processes between multiple processors each time they are
scheduled and rescheduled. Table 1 is an example of poor natural affinity; Table 2 shows what
good natural affinity looks like.

Table 1. The Ping-Pong Effect
          time 1 time 2 time 3 time 4

Process A CPU 0 CPU 1 CPU 0 CPU 1


Table 2. Good Affinity
          time 1 time 2 time 3 time 4

Process A CPU 0 CPU 0 CPU 0 CPU 0


Hard affinity, on the other hand, is what a CPU affinity system call provides. It is a requirement,
and processes must adhere to a specified hard affinity. If a processor is bound to CPU zero, for
example, then it can run only on CPU zero.
Why One Needs CPU Affinity

Before we cover the new system calls, let's discuss why anyone would need such a feature. The
first benefit of CPU affinity is optimizing cache performance. I said the O(1) scheduler tries hard
to keep tasks on the same processor, and it does. But in some performance-critical situations²
perhaps a large database or a highly threaded Java server²it makes sense to enforce the affinity
as a hard requirement. Multiprocessing computers go through a lot of trouble to keep the
processor caches valid. Data can be kept in only one processor's cache at a time. Otherwise, the
processor's cache may grow out of sync, leading to the question, who has the data that is the
most up-to-date copy of the main memory? Consequently, whenever a processor adds a line of
data to its local cache, all the other processors in the system also caching it must invalidate that
data. This invalidation is costly and unpleasant. But the real problem comes into play when
processes bounce between processors: they constantly cause cache invalidations, and the data
they want is never in the cache when they need it. Thus, cache miss rates grow very large. CPU
affinity protects against this and improves cache performance.

A second benefit of CPU affinity is a corollary to the first. If multiple threads are accessing the
same data, it might make sense to bind them all to the same processor. Doing so guarantees that
the threads do not contend over data and cause cache misses. This does diminish the performance
gained from multithreading on SMP. If the threads are inherently serialized, however, the
improved cache hit rate may be worth it.

The third and final benefit is found in real-time or otherwise time-sensitive applications. In this
approach, all the system processes are bound to a subset of the processors on the system. The
specialized application then is bound to the remaining processors. Commonly, in a dual-
processor system, the specialized application is bound to one processor, and all other processes
are bound to the other. This ensures that the specialized application receives the full attention of
the processor.

Affinity Masks

On most systems, Linux included, the interface for setting CPU affinity uses a bitmask. A
bitmask is a series of n bits, where each bit individually corresponds to the status of some other
object. For example, CPU affinity (on 32-bit machines) is represented by a 32-bit bitmask. Each
bit represents whether the given task is bound to the corresponding processor. Count the bits
from right to left, bit 0 to bit 31 and, thus, processor zero to processor 31. For example:

11111111111111111111111111111111 = 4,294,967,295

is the default CPU affinity mask for all processes. Because all bits are set, the process can run on
any processor. Conversely:

00000000000000000000000000000001 = 1
is much more restrictive. Only bit 0 is set, so the process may run only on processor zero. That
is, this affinity mask binds a process to processor zero.
Get it? What do the next two masks equal in decimal? What is the result of using them as the
affinity mask of a process?

10000000000000000000000000000000
00000000000000000000000000000011

The first is equal to 2,147,483,648 and, because bit 31 is set, binds the process to processor
number 31. The second is equal to 3, and it binds the process in question to processor zero and
processor one.

The Linux CPU affinity interface uses a bitmask like that shown above. Unfortunately, C does
not support binary constants, so you always have to use the decimal or hexadecimal equivalent.
You may get a compiler warning for very large decimal constants that set bit 31, but they will
work.

Using the New System Calls

With the correct kernel and glibc in hand, using the system calls is easy:

#define _GNU_SOURCE
#include <sched.h>
long
sched_setaffinity(pid_t pid, unsigned int len,
                  unsigned long *user_mask_ptr);
long
sched_getaffinity(pid_t pid, unsigned int len,
                  unsigned long *user_mask_ptr);

The first system call is used to set the affinity of a process, and the second system call retrieves
it.

In either system call, the PID argument is the PID of the process whose mask you wish to set or
retrieve. If the PID is set to zero, the PID of the current task is used.

The second argument is the length in bytes of the CPU affinity bitmask, currently four bytes (32
bits). This number is included in case the kernel ever changes the size of the CPU affinity mask
and allows the system calls to be forward-compatible with any changes; breaking syscalls is bad
form, after all. The third argument is a pointer to the bitmask itself.

Let us look at retrieving the CPU affinity of a task:

unsigned long mask;
unsigned int len = sizeof(mask);
if (sched_getaffinity(0, len, &mask) < 0) {
    perror("sched_getaffinity");
    return -1;
    }
printf("my affinity mask is: %08lxn", mask);
As a convenience, the returned mask is binary ANDed against the mask of all processors in the
system. Thus, processors in your system that are not on-line have corresponding bits that are not
set. For example, a uniprocessor system always returns 1 for the above call (bit 0 is set and no
others).

Setting the mask is equally easy:

unsigned long mask = 7; /* processors 0, 1, and 2 */
unsigned int len = sizeof(mask);
if (sched_setaffinity(0, len, &mask) < 0) {
    perror("sched_setaffinity");
}

This example binds the current process to the first three processors in the system.

You then can call sched_getaffinity() to ensure the change took effect. What does
sched_getaffinity() return for the above setup if you have only two processors? What if you have
only one? The system call fails unless at least one processor in the bitmask exists. Using a mask
of zero always fails. Likewise, binding to processor seven if you do not have a processor seven
will fail.

It is possible to retrieve the CPU affinity mask of any process on the system. You can set the
affinity of only the processes you own, however. Of course, root can set any process' affinity.

I Want a Tool!

If you are not a programmer, or if you cannot modify the source for whatever reason, you still
can bind processes. Listing 1 is the source code for a simple command-line utility to set the CPU
affinity mask of any process, given its PID. As we discussed above, you must own the process or
be root to do this.

Listing 1. bind (The whole program is given in the end of the article)

Usage is simple; once you learn the decimal equivalent of the CPU mask, you need:

usage: bind pid cpu_mask

As an example, assume we have a dual computer and want to bind our Quake process (with PID
1600) to processor two. We would enter the following:

bind 1600 2


Getting Really Crafty

In the previous example, we bound Quake to one of the two processors in our system. To ensure
top-notch frame rates, we need to bind all the other processes on the system to the other
processor. You can do this by hand or by writing a crafty script, but neither is efficient. Instead,
make use of the fact that CPU affinity is inherited across a fork(). All of a process' children
receive the same CPU affinity mask as their parent.

Then, all we need to do is have init bind itself to one processor. All other processes, by nature of
init being the root of the process tree and thus the superparent of all processes, are then likewise
bound to the one processor.

The cleanest way to do this type of bind is to hack this feature into init itself and pass in the
desired CPU affinity mask using the kernel command line. We can accomplish our goal with a
simpler solution, though, without having to modify and recompile init. Instead, we can edit the
system startup script. On most systems this is /etc/rc.d/rc.sysinit or /etc/rc.sysinit, the first script
run by init. Place the sample bind program in /bin, and add these lines to the start of rc.sysinit:

/bin/bind 1 1
/bin/bind $$ 1

These lines bind init (whose PID is one) and the current process to processor zero. All future
processes will fork from one of these two processes and thus inherit the CPU affinity mask. You
then can bind your process (whether it be a real-time nuclear control system or Quake) to
processor one. All processes will run on processor zero except our special process (and any
children), which will run on processor one. This ensures that the entire processor is available for
our special process.

Kernel Implementation of CPU Affinity

Long before Linus merged the CPU affinity system calls, the kernel supported and respected a
CPU affinity mask. There was no interface by which user space could set the mask.

Each process' mask is stored in its task_struct as an unsigned long, cpus_allowed. The
task_struct structure is called the process descriptor. It stores all the information about a process.
The CPU affinity interface merely reads and writes cpus_allowed.

Whenever the kernel attempts to migrate a process from one processor to another, it first checks
to see if the destination processor's bit is set in cpus_allowed. If the bit is not set, the kernel does
not migrate the process. Further, whenever the CPU affinity mask is changed, if the process is no
longer on an allowed processor it is migrated to one that is allowed. This ensures the process
begins on a legal processor and can migrate only to a legal processor. Of course, if it is bound to
only a single processor, it does not migrate anywhere.

Conclusion

The CPU affinity interface introduced in 2.5 and back-ported elsewhere provides a simple yet
powerful mechanism for controlling which processes are scheduled onto which processors. Users
with more than one processor may find the system calls useful in squeezing another drop of
performance out of their systems or for ensuring that processor time is available for even the
most demanding real-time task. Of course, users with only one processor need not feel left out.
They also can use the system calls, but they aren't going to be too useful.
Listing 1. bind
/* bind - simple command-line tool to set CPU
 * affinity of a given task
 */

#define _GNU_SOURCE

#include <stdlib.h>
#include <stdio.h>
#include <sched.h>

int main(int argc, char *argv[])
{
    unsigned long new_mask;
    unsigned long cur_mask;
    unsigned int len = sizeof(new_mask);
    pid_t pid;

    if (argc != 3) {
   fprintf(stderr,
                "usage: %s [pid] [cpu_mask]n",
                argv[0]);
   return -1;
    }

     pid = atol(argv[1]);
     sscanf(argv[2], "%08lx", &new_mask);

    if (sched_getaffinity(pid, len,
                          &cur_mask) < 0) {
   perror("sched_getaffinity");
   return -1;
    }

     printf("pid %d's old affinity: %08lxn",
            pid, cur_mask);

    if (sched_setaffinity(pid, len, &new_mask)) {
   perror("sched_setaffinity");
   return -1;
    }
if (sched_getaffinity(pid, len,
                           &cur_mask) < 0) {
    perror("sched_getaffinity");
    return -1;
     }

    printf(" pid %d's new affinity: %08lxn",
           pid, cur_mask);

    return 0;
}

Weitere ähnliche Inhalte

Was ist angesagt?

Ppt project process migration
Ppt project process migrationPpt project process migration
Ppt project process migrationjaya380
 
Process synchronization in Operating Systems
Process synchronization in Operating SystemsProcess synchronization in Operating Systems
Process synchronization in Operating SystemsRitu Ranjan Shrivastwa
 
VTU 5TH SEM CSE OPERATING SYSTEMS SOLVED PAPERS
VTU 5TH SEM CSE OPERATING SYSTEMS SOLVED PAPERSVTU 5TH SEM CSE OPERATING SYSTEMS SOLVED PAPERS
VTU 5TH SEM CSE OPERATING SYSTEMS SOLVED PAPERSvtunotesbysree
 
An eternal question of timing
An eternal question of timingAn eternal question of timing
An eternal question of timingPVS-Studio
 
Microkernels and Beyond
Microkernels and BeyondMicrokernels and Beyond
Microkernels and BeyondDavid Evans
 
FreeRTOS basics (Real time Operating System)
FreeRTOS basics (Real time Operating System)FreeRTOS basics (Real time Operating System)
FreeRTOS basics (Real time Operating System)Naren Chandra
 
Class 1: What is an Operating System?
Class 1: What is an Operating System?Class 1: What is an Operating System?
Class 1: What is an Operating System?David Evans
 
Cassandra运维之道 v0.2
Cassandra运维之道 v0.2Cassandra运维之道 v0.2
Cassandra运维之道 v0.2haiyuan ning
 
Process synchronizationfinal
Process synchronizationfinalProcess synchronizationfinal
Process synchronizationfinalmarangburu42
 
Different type of shells In Netapp Cluster mode 8.X and how to access them t...
Different type of shells In Netapp Cluster mode 8.X  and how to access them t...Different type of shells In Netapp Cluster mode 8.X  and how to access them t...
Different type of shells In Netapp Cluster mode 8.X and how to access them t...Saroj Sahu
 
streamparse and pystorm: simple reliable parallel processing with storm
streamparse and pystorm: simple reliable parallel processing with stormstreamparse and pystorm: simple reliable parallel processing with storm
streamparse and pystorm: simple reliable parallel processing with stormDaniel Blanchard
 
PART-1 : Mastering RTOS FreeRTOS and STM32Fx with Debugging
PART-1 : Mastering RTOS FreeRTOS and STM32Fx with DebuggingPART-1 : Mastering RTOS FreeRTOS and STM32Fx with Debugging
PART-1 : Mastering RTOS FreeRTOS and STM32Fx with DebuggingFastBit Embedded Brain Academy
 
Real-time streams and logs with Storm and Kafka
Real-time streams and logs with Storm and KafkaReal-time streams and logs with Storm and Kafka
Real-time streams and logs with Storm and KafkaAndrew Montalenti
 
Contiki introduction II-from what to how
Contiki introduction II-from what to howContiki introduction II-from what to how
Contiki introduction II-from what to howDingxin Xu
 
Processes, Threads and Scheduler
Processes, Threads and SchedulerProcesses, Threads and Scheduler
Processes, Threads and SchedulerMunazza-Mah-Jabeen
 

Was ist angesagt? (20)

.ppt
.ppt.ppt
.ppt
 
Ppt project process migration
Ppt project process migrationPpt project process migration
Ppt project process migration
 
Process synchronization in Operating Systems
Process synchronization in Operating SystemsProcess synchronization in Operating Systems
Process synchronization in Operating Systems
 
VTU 5TH SEM CSE OPERATING SYSTEMS SOLVED PAPERS
VTU 5TH SEM CSE OPERATING SYSTEMS SOLVED PAPERSVTU 5TH SEM CSE OPERATING SYSTEMS SOLVED PAPERS
VTU 5TH SEM CSE OPERATING SYSTEMS SOLVED PAPERS
 
An eternal question of timing
An eternal question of timingAn eternal question of timing
An eternal question of timing
 
Microkernels and Beyond
Microkernels and BeyondMicrokernels and Beyond
Microkernels and Beyond
 
FreeRTOS basics (Real time Operating System)
FreeRTOS basics (Real time Operating System)FreeRTOS basics (Real time Operating System)
FreeRTOS basics (Real time Operating System)
 
Class 1: What is an Operating System?
Class 1: What is an Operating System?Class 1: What is an Operating System?
Class 1: What is an Operating System?
 
Cassandra运维之道 v0.2
Cassandra运维之道 v0.2Cassandra运维之道 v0.2
Cassandra运维之道 v0.2
 
Process synchronizationfinal
Process synchronizationfinalProcess synchronizationfinal
Process synchronizationfinal
 
Different type of shells In Netapp Cluster mode 8.X and how to access them t...
Different type of shells In Netapp Cluster mode 8.X  and how to access them t...Different type of shells In Netapp Cluster mode 8.X  and how to access them t...
Different type of shells In Netapp Cluster mode 8.X and how to access them t...
 
streamparse and pystorm: simple reliable parallel processing with storm
streamparse and pystorm: simple reliable parallel processing with stormstreamparse and pystorm: simple reliable parallel processing with storm
streamparse and pystorm: simple reliable parallel processing with storm
 
PART-1 : Mastering RTOS FreeRTOS and STM32Fx with Debugging
PART-1 : Mastering RTOS FreeRTOS and STM32Fx with DebuggingPART-1 : Mastering RTOS FreeRTOS and STM32Fx with Debugging
PART-1 : Mastering RTOS FreeRTOS and STM32Fx with Debugging
 
Memory model
Memory modelMemory model
Memory model
 
Chapter05 new
Chapter05 newChapter05 new
Chapter05 new
 
Real-time streams and logs with Storm and Kafka
Real-time streams and logs with Storm and KafkaReal-time streams and logs with Storm and Kafka
Real-time streams and logs with Storm and Kafka
 
Contiki introduction II-from what to how
Contiki introduction II-from what to howContiki introduction II-from what to how
Contiki introduction II-from what to how
 
Unstuck
UnstuckUnstuck
Unstuck
 
Lab8
Lab8Lab8
Lab8
 
Processes, Threads and Scheduler
Processes, Threads and SchedulerProcesses, Threads and Scheduler
Processes, Threads and Scheduler
 

Ähnlich wie cpu-affinity

maXbox Starter 42 Multiprocessing Programming
maXbox Starter 42 Multiprocessing Programming maXbox Starter 42 Multiprocessing Programming
maXbox Starter 42 Multiprocessing Programming Max Kleiner
 
Operating Systems
Operating Systems Operating Systems
Operating Systems Fahad Shaikh
 
CS8603_Notes_003-1_edubuzz360.pdf
CS8603_Notes_003-1_edubuzz360.pdfCS8603_Notes_003-1_edubuzz360.pdf
CS8603_Notes_003-1_edubuzz360.pdfKishaKiddo
 
Interview questions
Interview questionsInterview questions
Interview questionsxavier john
 
Distributed system lectures
Distributed system lecturesDistributed system lectures
Distributed system lecturesmarwaeng
 
LM1 - Computer System Overview, system calls
LM1 - Computer System Overview, system callsLM1 - Computer System Overview, system calls
LM1 - Computer System Overview, system callsmanideepakc
 
Multithreading 101
Multithreading 101Multithreading 101
Multithreading 101Tim Penhey
 
intro, definitions, basic laws+.pptx
intro, definitions, basic laws+.pptxintro, definitions, basic laws+.pptx
intro, definitions, basic laws+.pptxssuser413a98
 
Clustering Manual for Parallel Computing
Clustering Manual for Parallel ComputingClustering Manual for Parallel Computing
Clustering Manual for Parallel ComputingMamun Ahmed
 
Building A Linux Cluster Using Raspberry PI #2!
Building A Linux Cluster Using Raspberry PI #2!Building A Linux Cluster Using Raspberry PI #2!
Building A Linux Cluster Using Raspberry PI #2!A Jorge Garcia
 
IRJET- Latin Square Computation of Order-3 using Open CL
IRJET- Latin Square Computation of Order-3 using Open CLIRJET- Latin Square Computation of Order-3 using Open CL
IRJET- Latin Square Computation of Order-3 using Open CLIRJET Journal
 

Ähnlich wie cpu-affinity (20)

maXbox Starter 42 Multiprocessing Programming
maXbox Starter 42 Multiprocessing Programming maXbox Starter 42 Multiprocessing Programming
maXbox Starter 42 Multiprocessing Programming
 
Operating Systems
Operating Systems Operating Systems
Operating Systems
 
Os notes
Os notesOs notes
Os notes
 
Linux scheduler
Linux schedulerLinux scheduler
Linux scheduler
 
CS8603_Notes_003-1_edubuzz360.pdf
CS8603_Notes_003-1_edubuzz360.pdfCS8603_Notes_003-1_edubuzz360.pdf
CS8603_Notes_003-1_edubuzz360.pdf
 
Chapter 10
Chapter 10Chapter 10
Chapter 10
 
Interview questions
Interview questionsInterview questions
Interview questions
 
Distributed system lectures
Distributed system lecturesDistributed system lectures
Distributed system lectures
 
LM1 - Computer System Overview, system calls
LM1 - Computer System Overview, system callsLM1 - Computer System Overview, system calls
LM1 - Computer System Overview, system calls
 
1844 1849
1844 18491844 1849
1844 1849
 
1844 1849
1844 18491844 1849
1844 1849
 
Coa presentation5
Coa presentation5Coa presentation5
Coa presentation5
 
Computer Science Assignment Help
Computer Science Assignment HelpComputer Science Assignment Help
Computer Science Assignment Help
 
Multithreading 101
Multithreading 101Multithreading 101
Multithreading 101
 
intro, definitions, basic laws+.pptx
intro, definitions, basic laws+.pptxintro, definitions, basic laws+.pptx
intro, definitions, basic laws+.pptx
 
fall2013
fall2013fall2013
fall2013
 
Clustering Manual for Parallel Computing
Clustering Manual for Parallel ComputingClustering Manual for Parallel Computing
Clustering Manual for Parallel Computing
 
100-E
100-E100-E
100-E
 
Building A Linux Cluster Using Raspberry PI #2!
Building A Linux Cluster Using Raspberry PI #2!Building A Linux Cluster Using Raspberry PI #2!
Building A Linux Cluster Using Raspberry PI #2!
 
IRJET- Latin Square Computation of Order-3 using Open CL
IRJET- Latin Square Computation of Order-3 using Open CLIRJET- Latin Square Computation of Order-3 using Open CL
IRJET- Latin Square Computation of Order-3 using Open CL
 

Kürzlich hochgeladen

How to write a Business Continuity Plan
How to write a Business Continuity PlanHow to write a Business Continuity Plan
How to write a Business Continuity PlanDatabarracks
 
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...Alkin Tezuysal
 
TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024Lonnie McRorey
 
A Deep Dive on Passkeys: FIDO Paris Seminar.pptx
A Deep Dive on Passkeys: FIDO Paris Seminar.pptxA Deep Dive on Passkeys: FIDO Paris Seminar.pptx
A Deep Dive on Passkeys: FIDO Paris Seminar.pptxLoriGlavin3
 
Genislab builds better products and faster go-to-market with Lean project man...
Genislab builds better products and faster go-to-market with Lean project man...Genislab builds better products and faster go-to-market with Lean project man...
Genislab builds better products and faster go-to-market with Lean project man...Farhan Tariq
 
Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)Kaya Weers
 
React Native vs Ionic - The Best Mobile App Framework
React Native vs Ionic - The Best Mobile App FrameworkReact Native vs Ionic - The Best Mobile App Framework
React Native vs Ionic - The Best Mobile App FrameworkPixlogix Infotech
 
QCon London: Mastering long-running processes in modern architectures
QCon London: Mastering long-running processes in modern architecturesQCon London: Mastering long-running processes in modern architectures
QCon London: Mastering long-running processes in modern architecturesBernd Ruecker
 
2024 April Patch Tuesday
2024 April Patch Tuesday2024 April Patch Tuesday
2024 April Patch TuesdayIvanti
 
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024BookNet Canada
 
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptxPasskey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptxLoriGlavin3
 
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...Wes McKinney
 
TrustArc Webinar - How to Build Consumer Trust Through Data Privacy
TrustArc Webinar - How to Build Consumer Trust Through Data PrivacyTrustArc Webinar - How to Build Consumer Trust Through Data Privacy
TrustArc Webinar - How to Build Consumer Trust Through Data PrivacyTrustArc
 
Data governance with Unity Catalog Presentation
Data governance with Unity Catalog PresentationData governance with Unity Catalog Presentation
Data governance with Unity Catalog PresentationKnoldus Inc.
 
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024BookNet Canada
 
Top 10 Hubspot Development Companies in 2024
Top 10 Hubspot Development Companies in 2024Top 10 Hubspot Development Companies in 2024
Top 10 Hubspot Development Companies in 2024TopCSSGallery
 
Long journey of Ruby standard library at RubyConf AU 2024
Long journey of Ruby standard library at RubyConf AU 2024Long journey of Ruby standard library at RubyConf AU 2024
Long journey of Ruby standard library at RubyConf AU 2024Hiroshi SHIBATA
 
Generative AI - Gitex v1Generative AI - Gitex v1.pptx
Generative AI - Gitex v1Generative AI - Gitex v1.pptxGenerative AI - Gitex v1Generative AI - Gitex v1.pptx
Generative AI - Gitex v1Generative AI - Gitex v1.pptxfnnc6jmgwh
 
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxThe Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxLoriGlavin3
 
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...Nikki Chapple
 

Kürzlich hochgeladen (20)

How to write a Business Continuity Plan
How to write a Business Continuity PlanHow to write a Business Continuity Plan
How to write a Business Continuity Plan
 
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
Unleashing Real-time Insights with ClickHouse_ Navigating the Landscape in 20...
 
TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024
 
A Deep Dive on Passkeys: FIDO Paris Seminar.pptx
A Deep Dive on Passkeys: FIDO Paris Seminar.pptxA Deep Dive on Passkeys: FIDO Paris Seminar.pptx
A Deep Dive on Passkeys: FIDO Paris Seminar.pptx
 
Genislab builds better products and faster go-to-market with Lean project man...
Genislab builds better products and faster go-to-market with Lean project man...Genislab builds better products and faster go-to-market with Lean project man...
Genislab builds better products and faster go-to-market with Lean project man...
 
Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)Design pattern talk by Kaya Weers - 2024 (v2)
Design pattern talk by Kaya Weers - 2024 (v2)
 
React Native vs Ionic - The Best Mobile App Framework
React Native vs Ionic - The Best Mobile App FrameworkReact Native vs Ionic - The Best Mobile App Framework
React Native vs Ionic - The Best Mobile App Framework
 
QCon London: Mastering long-running processes in modern architectures
QCon London: Mastering long-running processes in modern architecturesQCon London: Mastering long-running processes in modern architectures
QCon London: Mastering long-running processes in modern architectures
 
2024 April Patch Tuesday
2024 April Patch Tuesday2024 April Patch Tuesday
2024 April Patch Tuesday
 
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
 
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptxPasskey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptx
 
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
 
TrustArc Webinar - How to Build Consumer Trust Through Data Privacy
TrustArc Webinar - How to Build Consumer Trust Through Data PrivacyTrustArc Webinar - How to Build Consumer Trust Through Data Privacy
TrustArc Webinar - How to Build Consumer Trust Through Data Privacy
 
Data governance with Unity Catalog Presentation
Data governance with Unity Catalog PresentationData governance with Unity Catalog Presentation
Data governance with Unity Catalog Presentation
 
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
 
Top 10 Hubspot Development Companies in 2024
Top 10 Hubspot Development Companies in 2024Top 10 Hubspot Development Companies in 2024
Top 10 Hubspot Development Companies in 2024
 
Long journey of Ruby standard library at RubyConf AU 2024
Long journey of Ruby standard library at RubyConf AU 2024Long journey of Ruby standard library at RubyConf AU 2024
Long journey of Ruby standard library at RubyConf AU 2024
 
Generative AI - Gitex v1Generative AI - Gitex v1.pptx
Generative AI - Gitex v1Generative AI - Gitex v1.pptxGenerative AI - Gitex v1Generative AI - Gitex v1.pptx
Generative AI - Gitex v1Generative AI - Gitex v1.pptx
 
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxThe Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
 
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...
Microsoft 365 Copilot: How to boost your productivity with AI – Part one: Ado...
 

cpu-affinity

  • 1. CPU Affinity Bind specific processes to specific processors with a new system call. The ability in Linux to bind one or more processes to one or more processors, called CPU affinity, is a long-requested feature. The idea is to say ³always run this process on processor one´ or ³run these processes on all processors but processor zero´. The scheduler then obeys the order, and the process runs only on the allowed processors. Other operating systems, such as Windows NT, have long provided a system call to set the CPU affinity for a process. Consequently, demand for such a system call in Linux has been high. Finally, the 2.5 kernel introduced a set of system calls for setting and retrieving the CPU affinity of a process. In this article, I look at the reasons for introducing a CPU affinity interface to Linux. I then cover how to use the interface in your programs. If you are not a programmer or if you have an existing program you are unable to modify, I cover a simple utility for changing the affinity of a given process using its PID. Finally, we look at the actual implementation of the system call. Soft vs. Hard CPU Affinity There are two types of CPU affinity. The first, soft affinity, also called natural affinity, is the tendency of a scheduler to try to keep processes on the same CPU as long as possible. It is merely an attempt; if it is ever infeasible, the processes certainly will migrate to another processor. The new O(1) scheduler in 2.5 exhibits excellent natural affinity. On the opposite end, however, is the 2.4 scheduler, which has poor CPU affinity. This behavior results in the ping- pong effect. The scheduler bounces processes between multiple processors each time they are scheduled and rescheduled. Table 1 is an example of poor natural affinity; Table 2 shows what good natural affinity looks like. Table 1. The Ping-Pong Effect time 1 time 2 time 3 time 4 Process A CPU 0 CPU 1 CPU 0 CPU 1 Table 2. Good Affinity time 1 time 2 time 3 time 4 Process A CPU 0 CPU 0 CPU 0 CPU 0 Hard affinity, on the other hand, is what a CPU affinity system call provides. It is a requirement, and processes must adhere to a specified hard affinity. If a processor is bound to CPU zero, for example, then it can run only on CPU zero.
  • 2. Why One Needs CPU Affinity Before we cover the new system calls, let's discuss why anyone would need such a feature. The first benefit of CPU affinity is optimizing cache performance. I said the O(1) scheduler tries hard to keep tasks on the same processor, and it does. But in some performance-critical situations² perhaps a large database or a highly threaded Java server²it makes sense to enforce the affinity as a hard requirement. Multiprocessing computers go through a lot of trouble to keep the processor caches valid. Data can be kept in only one processor's cache at a time. Otherwise, the processor's cache may grow out of sync, leading to the question, who has the data that is the most up-to-date copy of the main memory? Consequently, whenever a processor adds a line of data to its local cache, all the other processors in the system also caching it must invalidate that data. This invalidation is costly and unpleasant. But the real problem comes into play when processes bounce between processors: they constantly cause cache invalidations, and the data they want is never in the cache when they need it. Thus, cache miss rates grow very large. CPU affinity protects against this and improves cache performance. A second benefit of CPU affinity is a corollary to the first. If multiple threads are accessing the same data, it might make sense to bind them all to the same processor. Doing so guarantees that the threads do not contend over data and cause cache misses. This does diminish the performance gained from multithreading on SMP. If the threads are inherently serialized, however, the improved cache hit rate may be worth it. The third and final benefit is found in real-time or otherwise time-sensitive applications. In this approach, all the system processes are bound to a subset of the processors on the system. The specialized application then is bound to the remaining processors. Commonly, in a dual- processor system, the specialized application is bound to one processor, and all other processes are bound to the other. This ensures that the specialized application receives the full attention of the processor. Affinity Masks On most systems, Linux included, the interface for setting CPU affinity uses a bitmask. A bitmask is a series of n bits, where each bit individually corresponds to the status of some other object. For example, CPU affinity (on 32-bit machines) is represented by a 32-bit bitmask. Each bit represents whether the given task is bound to the corresponding processor. Count the bits from right to left, bit 0 to bit 31 and, thus, processor zero to processor 31. For example: 11111111111111111111111111111111 = 4,294,967,295 is the default CPU affinity mask for all processes. Because all bits are set, the process can run on any processor. Conversely: 00000000000000000000000000000001 = 1 is much more restrictive. Only bit 0 is set, so the process may run only on processor zero. That is, this affinity mask binds a process to processor zero.
  • 3. Get it? What do the next two masks equal in decimal? What is the result of using them as the affinity mask of a process? 10000000000000000000000000000000 00000000000000000000000000000011 The first is equal to 2,147,483,648 and, because bit 31 is set, binds the process to processor number 31. The second is equal to 3, and it binds the process in question to processor zero and processor one. The Linux CPU affinity interface uses a bitmask like that shown above. Unfortunately, C does not support binary constants, so you always have to use the decimal or hexadecimal equivalent. You may get a compiler warning for very large decimal constants that set bit 31, but they will work. Using the New System Calls With the correct kernel and glibc in hand, using the system calls is easy: #define _GNU_SOURCE #include <sched.h> long sched_setaffinity(pid_t pid, unsigned int len, unsigned long *user_mask_ptr); long sched_getaffinity(pid_t pid, unsigned int len, unsigned long *user_mask_ptr); The first system call is used to set the affinity of a process, and the second system call retrieves it. In either system call, the PID argument is the PID of the process whose mask you wish to set or retrieve. If the PID is set to zero, the PID of the current task is used. The second argument is the length in bytes of the CPU affinity bitmask, currently four bytes (32 bits). This number is included in case the kernel ever changes the size of the CPU affinity mask and allows the system calls to be forward-compatible with any changes; breaking syscalls is bad form, after all. The third argument is a pointer to the bitmask itself. Let us look at retrieving the CPU affinity of a task: unsigned long mask; unsigned int len = sizeof(mask); if (sched_getaffinity(0, len, &mask) < 0) { perror("sched_getaffinity"); return -1; } printf("my affinity mask is: %08lxn", mask);
  • 4. As a convenience, the returned mask is binary ANDed against the mask of all processors in the system. Thus, processors in your system that are not on-line have corresponding bits that are not set. For example, a uniprocessor system always returns 1 for the above call (bit 0 is set and no others). Setting the mask is equally easy: unsigned long mask = 7; /* processors 0, 1, and 2 */ unsigned int len = sizeof(mask); if (sched_setaffinity(0, len, &mask) < 0) { perror("sched_setaffinity"); } This example binds the current process to the first three processors in the system. You then can call sched_getaffinity() to ensure the change took effect. What does sched_getaffinity() return for the above setup if you have only two processors? What if you have only one? The system call fails unless at least one processor in the bitmask exists. Using a mask of zero always fails. Likewise, binding to processor seven if you do not have a processor seven will fail. It is possible to retrieve the CPU affinity mask of any process on the system. You can set the affinity of only the processes you own, however. Of course, root can set any process' affinity. I Want a Tool! If you are not a programmer, or if you cannot modify the source for whatever reason, you still can bind processes. Listing 1 is the source code for a simple command-line utility to set the CPU affinity mask of any process, given its PID. As we discussed above, you must own the process or be root to do this. Listing 1. bind (The whole program is given in the end of the article) Usage is simple; once you learn the decimal equivalent of the CPU mask, you need: usage: bind pid cpu_mask As an example, assume we have a dual computer and want to bind our Quake process (with PID 1600) to processor two. We would enter the following: bind 1600 2 Getting Really Crafty In the previous example, we bound Quake to one of the two processors in our system. To ensure top-notch frame rates, we need to bind all the other processes on the system to the other processor. You can do this by hand or by writing a crafty script, but neither is efficient. Instead,
  • 5. make use of the fact that CPU affinity is inherited across a fork(). All of a process' children receive the same CPU affinity mask as their parent. Then, all we need to do is have init bind itself to one processor. All other processes, by nature of init being the root of the process tree and thus the superparent of all processes, are then likewise bound to the one processor. The cleanest way to do this type of bind is to hack this feature into init itself and pass in the desired CPU affinity mask using the kernel command line. We can accomplish our goal with a simpler solution, though, without having to modify and recompile init. Instead, we can edit the system startup script. On most systems this is /etc/rc.d/rc.sysinit or /etc/rc.sysinit, the first script run by init. Place the sample bind program in /bin, and add these lines to the start of rc.sysinit: /bin/bind 1 1 /bin/bind $$ 1 These lines bind init (whose PID is one) and the current process to processor zero. All future processes will fork from one of these two processes and thus inherit the CPU affinity mask. You then can bind your process (whether it be a real-time nuclear control system or Quake) to processor one. All processes will run on processor zero except our special process (and any children), which will run on processor one. This ensures that the entire processor is available for our special process. Kernel Implementation of CPU Affinity Long before Linus merged the CPU affinity system calls, the kernel supported and respected a CPU affinity mask. There was no interface by which user space could set the mask. Each process' mask is stored in its task_struct as an unsigned long, cpus_allowed. The task_struct structure is called the process descriptor. It stores all the information about a process. The CPU affinity interface merely reads and writes cpus_allowed. Whenever the kernel attempts to migrate a process from one processor to another, it first checks to see if the destination processor's bit is set in cpus_allowed. If the bit is not set, the kernel does not migrate the process. Further, whenever the CPU affinity mask is changed, if the process is no longer on an allowed processor it is migrated to one that is allowed. This ensures the process begins on a legal processor and can migrate only to a legal processor. Of course, if it is bound to only a single processor, it does not migrate anywhere. Conclusion The CPU affinity interface introduced in 2.5 and back-ported elsewhere provides a simple yet powerful mechanism for controlling which processes are scheduled onto which processors. Users with more than one processor may find the system calls useful in squeezing another drop of performance out of their systems or for ensuring that processor time is available for even the most demanding real-time task. Of course, users with only one processor need not feel left out. They also can use the system calls, but they aren't going to be too useful.
  • 6. Listing 1. bind /* bind - simple command-line tool to set CPU * affinity of a given task */ #define _GNU_SOURCE #include <stdlib.h> #include <stdio.h> #include <sched.h> int main(int argc, char *argv[]) { unsigned long new_mask; unsigned long cur_mask; unsigned int len = sizeof(new_mask); pid_t pid; if (argc != 3) { fprintf(stderr, "usage: %s [pid] [cpu_mask]n", argv[0]); return -1; } pid = atol(argv[1]); sscanf(argv[2], "%08lx", &new_mask); if (sched_getaffinity(pid, len, &cur_mask) < 0) { perror("sched_getaffinity"); return -1; } printf("pid %d's old affinity: %08lxn", pid, cur_mask); if (sched_setaffinity(pid, len, &new_mask)) { perror("sched_setaffinity"); return -1; }
  • 7. if (sched_getaffinity(pid, len, &cur_mask) < 0) { perror("sched_getaffinity"); return -1; } printf(" pid %d's new affinity: %08lxn", pid, cur_mask); return 0; }