How can I know in a C program, on which physical processor and core my code is running? I\'m using Linux and gcc 4.4.3.
You may check /proc//stat file system, according to http://www.kernel.org/doc/Documentation/filesystems/proc.txt, you should just check task_cpu flag.
As example without correct types and error checking:
struct pstat
{
int pid; //process id
char tcomm[256];//filename of the executable
char state[2]; //state (R is running, S is sleeping, D is sleeping in an
//uninterruptible wait, Z is zombie, T is traced or stopped)
int ppid;// process id of the parent process
int pgrp;// pgrp of the process
int sid;// session id
int tty_nr;// tty the process uses
int tty_pgrp;// pgrp of the tty
int flags;// task flags
int min_flt;// number of minor faults
int cmin_flt;// number of minor faults with child's
int maj_flt;// number of major faults
int cmaj_flt;// number of major faults with child's
int utime;// user mode jiffies
int stime;// kernel mode jiffies
int cutime;// user mode jiffies with child's
int cstime;// kernel mode jiffies with child's
int priority;// priority level
int nice;// nice level
int num_threads;// number of threads
int it_real_value;// (obsolete, always 0)
int start_time;// time the process started after system boot
int vsize;// virtual memory size
int rss;// resident set memory size
int rsslim;// current limit in bytes on the rss
int start_code;// address above which program text can run
int end_code;// address below which program text can run
int start_stack;// address of the start of the stack
int esp;// current value of ESP
int eip;// current value of EIP
int pending;// bitmap of pending signals
int blocked;// bitmap of blocked signals
int sigign;// bitmap of ignored signals
int sigcatch;// bitmap of catched signals
int wchan;// address where process went to sleep
int i0;// (place holder)
int i1;// (place holder)
int exit_signal;// signal to send to parent thread on exit
int task_cpu;// which CPU the task is scheduled on
int rt_priority;// realtime priority
int policy;// scheduling policy (man sched_setscheduler)
int blkio_ticks;// time spent waiting for block IO
int gtime;// guest time of the task in jiffies
int cgtime;// guest time of the task children in jiffies
} p ;
int main()
{
char name[256];
char state[8];
FILE* f = fopen("/proc/self/stat", "r");
fscanf(f, "%d%s%s%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d%d",
&p.pid, &p.tcomm, &p.state, &p.ppid, &p.pgrp, &p.sid, &p.tty_nr, &p.tty_pgrp, &p.flags,
&p.min_flt, &p.cmin_flt, &p.maj_flt, &p.cmaj_flt, &p.utime, &p.stime, &p.cutime, &p.cstime,
&p.priority, &p.nice, &p.num_threads, &p.it_real_value, &p.start_time, &p.vsize, &p.rss,
&p.rsslim, &p.start_code, &p.end_code, &p.start_stack, &p.esp, &p.eip, &p.pending, &p.blocked,
&p.sigign, &p.sigcatch, &p.wchan, &p.i0, &p.i1, &p.exit_signal, &p.task_cpu, &p.rt_priority, &p.policy,
&p.blkio_ticks, &p.gtime, &p.cgtime);
printf("CPU %d\n", p.task_cpu);
return 0;
}
You can get the affinity of the process to a processor using GCC. The CPU affinity APIs might help you out. Are you trying to use this information to ensure your process is not interrupted or such high priority task?
See http://en.wikipedia.org/wiki/CPUID#Accessing_the_id_from_other_languages
What you want is the APIC ID... basically:
cpuid
shr ebx, 24
By and large it's hard to find this out in a meaningful way. Your thread will often run on many different processors during its life. You could call a function to ask which processor you are on and get a context switch whilst the function is executing. What should the function return?
sched_getcpu()
call returns virtual CPU number. Mapping of virtual CPU to real CPU info is in /proc/cpuinfo.
If your system supports VDSO, then sched_getcpu()
is relatively fast.
CPU number can be also obtained using CPUID
instruction, but it is slower than sched_getcpu()
.