title: How many threads per core?
body: <p>I am running a multi-threaded program on my computer which has <strong>4 cores</strong>. I am creating threads that run with SCHED_FIFO, SCHED_OTHER, and SCHED_RR priorities. What is the maximum number of each type of thread that can run simultaneously? </p>
  
  <p>For example, 
  I'm pretty sure only four SCHED_FIFO threads can run at a time (one per core)
  but I'm not sure about the other two.</p>
  
  <p><em>edit</em> my code, as asked (it's long, but most of it is for testing how long each thread completes a delay task)</p>
  
  <pre><code>#include &lt;stdio.h&gt;
  #include &lt;stdlib.h&gt;
  #include &lt;unistd.h&gt;
  #include &lt;pthread.h&gt;
  #include &lt;sys/time.h&gt;
  #include &lt;time.h&gt;
  #include &lt;string.h&gt;
  
  void *ThreadRunner(void *vargp);
  void DisplayThreadSchdStats(void);
  void delayTask(void);
  
  int threadNumber = 0;
  pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
  pthread_cond_t cond = PTHREAD_COND_INITIALIZER;
  
  #define NUM_THREADS    9
  
  //used to store the information of each thread
  typedef struct{
      pthread_t  threadID;
      int policy;
      struct sched_param param;
      long startTime;
      long taskStartTime;
      long endTime1;
      long endTime2;
      long endTime3;
      long runTime;
      char startDate[30];
      char endDate[30];
  }ThreadInfo;
  
  ThreadInfo myThreadInfo[NUM_THREADS];
  
  
  
  //main function
  int main(void){
  
     printf("running...\n");
  
     int fifoPri = 60;
     int rrPri = 30;
  
     //create the 9 threads and assign their scheduling policies
     for(int i=0; i&lt;NUM_THREADS; i++){
  
         if(i%3 == SCHED_OTHER){
              myThreadInfo[i].policy = SCHED_OTHER;
              myThreadInfo[i].param.sched_priority = 0;
         }
         else if (i%3 == SCHED_FIFO){ 
              myThreadInfo[i].policy = SCHED_RR;
              myThreadInfo[i].param.sched_priority = rrPri++; 
         }
         else{
              myThreadInfo[i].policy = SCHED_FIFO; 
              myThreadInfo[i].param.sched_priority = fifoPri++; 
         }
         pthread_create( &amp;myThreadInfo[i].threadID, NULL, ThreadRunner, &amp;myThreadInfo[i]);
  pthread_cond_wait(&amp;cond, &amp;mutex);
     }
  
     printf("\n\n");
  
  
     //join each thread
     for(int g = 0; g &lt; NUM_THREADS; g++){
        pthread_join(myThreadInfo[g].threadID, NULL);
     }
  
  
     //print out the stats for each thread
     DisplayThreadSchdStats();
  
  
     return 0;
  }
  
  
  //used to print out all of the threads, along with their stats
  void DisplayThreadSchdStats(void){
  
     int otherNum = 0;
     long task1RR = 0;
     long task2RR = 0;
     long task3RR = 0;
     long task1FIFO = 0;
     long task2FIFO = 0;
     long task3FIFO = 0;
     long task1OTHER = 0;
     long task2OTHER = 0;
     long task3OTHER = 0;
  
     for(int g = 0; g &lt; threadNumber; g++){
  
        printf("\nThread# [%d]  id [0x%x] exiting...\n", g + 1, (int) myThreadInfo[g].threadID);
        printf("DisplayThreadSchdStats:\n");
        printf("   threadID    = 0x%x \n", (int) myThreadInfo[g].threadID);
  
        if(myThreadInfo[g].policy == 0){
           printf("   policy      = SHED_OTHER\n");
           task1OTHER += (myThreadInfo[g].endTime1 - myThreadInfo[g].taskStartTime); 
           task2OTHER += (myThreadInfo[g].endTime2 - myThreadInfo[g].endTime1);
           task3OTHER += (myThreadInfo[g].endTime3 - myThreadInfo[g].endTime2);
           otherNum++;
        }
        if(myThreadInfo[g].policy == 1){
           printf("   policy      = SHED_FIFO\n");
           task1FIFO += (myThreadInfo[g].endTime1 - myThreadInfo[g].taskStartTime); 
           task2FIFO += (myThreadInfo[g].endTime2 - myThreadInfo[g].endTime1);
           task3FIFO += (myThreadInfo[g].endTime3 - myThreadInfo[g].endTime2);
  
        }
        if(myThreadInfo[g].policy == 2){
           printf("   policy      = SHED_RR\n");
           task1RR+= (myThreadInfo[g].endTime1 - myThreadInfo[g].taskStartTime); 
           task2RR += (myThreadInfo[g].endTime2 - myThreadInfo[g].endTime1);
           task3RR += (myThreadInfo[g].endTime3 - myThreadInfo[g].endTime2);
  
        }
  
  
  
        printf("   priority    = %d \n", myThreadInfo[g].param.sched_priority);
        printf("   startTime   = %s\n", myThreadInfo[g].startDate);
        printf("   endTime     = %s\n", myThreadInfo[g].endDate);
        printf("   Task start TimeStamp in micro seconds [%ld]\n", myThreadInfo[g].taskStartTime);
        printf("   Task end   TimeStamp in micro seconds [%ld] Delta [%lu]us\n", myThreadInfo[g].endTime1 , (myThreadInfo[g].endTime1 - myThreadInfo[g].taskStartTime));
        printf("   Task end   Timestamp in micro seconds [%ld] Delta [%lu]us\n", myThreadInfo[g].endTime2, (myThreadInfo[g].endTime2 - myThreadInfo[g].endTime1));
        printf("   Task end   Timestamp in micro seconds [%ld] Delta [%lu]us\n\n\n", myThreadInfo[g].endTime3, (myThreadInfo[g].endTime3 - myThreadInfo[g].endTime2));
        printf("\n\n");
  
  
     }
  
     printf("Analysis: \n");
     printf("  for SCHED_OTHER, task 1 took %lu,  task2 took %lu,  and task 3 took %lu.   (average = %lu)\n", (task1OTHER/otherNum), (task2OTHER/otherNum), (task3OTHER/otherNum), (task1OTHER/otherNum + task2OTHER/otherNum + task3OTHER/otherNum)/3 );
     printf("  for SCHED_RR,    task 1 took %lu,  task2 took %lu,  and task 3 took %lu.   (average = %lu)\n", (task1RR/otherNum), (task2RR/otherNum), (task3RR/otherNum), (task1RR/otherNum + task2RR/otherNum + task3RR/otherNum)/3 );
     printf("  for SCHED_FIFO,  task 1 took %lu,  task2 took %lu,  and task 3 took %lu.   (average = %lu)\n", (task1FIFO/otherNum), (task2FIFO/otherNum), (task3FIFO/otherNum) , (task1FIFO/otherNum + task2FIFO/otherNum + task3FIFO/otherNum)/3);
  
  }
  
  
  
  
  
  //the function that runs the threads
  void *ThreadRunner(void *vargp){
  
  
     pthread_mutex_lock(&amp;mutex);
  
  
     char date[30];
     struct tm *ts;
     size_t last;
     time_t timestamp = time(NULL);
     ts = localtime(&amp;timestamp);
     last = strftime(date, 30, "%c", ts);
     threadNumber++;
     ThreadInfo* currentThread;
     currentThread = (ThreadInfo*)vargp;
  
  
     //set the start time
     struct timeval  tv;
     gettimeofday(&amp;tv, NULL);
     long milltime0 = (tv.tv_sec) * 1000 + (tv.tv_usec) / 1000;
     currentThread-&gt;startTime = milltime0;
  
     //set the start date
     strcpy(currentThread-&gt;startDate, date);
  
     if(pthread_setschedparam(pthread_self(), currentThread-&gt;policy,(const struct sched_param *) &amp;(currentThread-&gt;param))){
        perror("pthread_setschedparam failed");
        pthread_exit(NULL);
     }
  
     if(pthread_getschedparam(pthread_self(), &amp;currentThread-&gt;policy,(struct sched_param *) &amp;currentThread-&gt;param)){
        perror("pthread_getschedparam failed");
        pthread_exit(NULL);
     }
  
     gettimeofday(&amp;tv, NULL);
     long startTime = (tv.tv_sec) * 1000 + (tv.tv_usec) / 1000;
     currentThread-&gt;taskStartTime = startTime;
     //delay task #1
     delayTask();
  
     //set the end time of task 1
     gettimeofday(&amp;tv, NULL);
     long milltime1 = (tv.tv_sec) * 1000 + (tv.tv_usec) / 1000;
     currentThread-&gt;endTime1 = milltime1;
  
  
     //delay task #2
     delayTask();
  
     //set the end time of task 2
     gettimeofday(&amp;tv, NULL);
     long milltime2 = (tv.tv_sec) * 1000 + (tv.tv_usec) / 1000;
     currentThread-&gt;endTime2 = milltime2;
  
  
     //delay task #3
     delayTask();
  
     //set the end time of task 3
     gettimeofday(&amp;tv, NULL);
     long milltime3 = (tv.tv_sec) * 1000 + (tv.tv_usec) / 1000;
     currentThread-&gt;endTime3 = milltime3;
  
  
     //set the end date
     timestamp = time(NULL);
     ts = localtime(&amp;timestamp);
     last = strftime(date, 30, "%c", ts);
     strcpy(currentThread-&gt;endDate, date);
  
  
     //set the total run time of the thread
     long runTime = milltime3 - milltime0;
     currentThread-&gt;runTime = runTime;
  
     //unlock mutex
     pthread_mutex_unlock(&amp;mutex);
     pthread_cond_signal(&amp;cond);
  
     pthread_exit(NULL);
  }
  
  //used to delay each thread
  void delayTask(void){
     for(int i = 0; i &lt; 5000000; i++){
        printf("%d", i % 2);
     }
  
  }
  </code></pre>