2012-01-25 26 views
16

¿Hay alguna forma de determinar en qué CPU se ejecuta un hilo determinado? Preferiblemente en C#, pero C++ sería suficiente.¿Cómo determinar en qué CPU se ejecuta un subproceso?

Las clases .NET Process y ProcessThread no parecen proporcionar esta información.

ETA Aclaraciones:

estamos desarrollando una aplicación de servidor que procesa http secuencias de multidifusión y genera múltiples codificadores de vídeo. Esto se ejecuta en un sistema con 12 núcleos físicos, lo que resulta en 24 CPU lógicas (hyperthreading). A través de TaskManager y ProcessExplorer, hemos verificado que nuestros procesos generados se distribuyen uniformemente sobre las CPU lógicas. Sin embargo, estamos viendo una gran cantidad de actividad (kernel?) En una sola CPU que interfiere al consumir cantidades inusuales de tiempo de CPU. Estamos tratando de identificar qué proceso (s)/thread (s) se están ejecutando en esta CPU en particular. Ni TaskManager ni ProcessExplorer parecen proporcionar esa información. Si lo hacen, explique cómo se puede obtener dicha información.

De lo contrario, estamos pensando en escribir nuestra propia herramienta para obtener esta información. Y eso es con lo que necesitamos ayuda.

Sabemos cómo cambiar la afinidad de un subproceso (y sabemos que no hay garantía de que un subproceso permanezca asociado a ninguna CPU, aunque en este caso particular el subproceso que consume CPU permanece asociado con solo una CPU), pero para poder hacerlo, primero debemos determinar QUÉ proceso/hilo necesita ser reubicado. Ese es el único objetivo de esta pregunta.

Espero que esto ayude a aclarar el problema.

+7

¿Qué problema está tratando de resolver con esta información? –

+0

Es conocido solo por el kernal. Entonces necesitas programar en modo Kernal. Busque las API de Kernal en MSDN. – Nawaz

+2

¿Qué le gustaría que hiciera si un subproceso se ejecutara en muchas CPU diferentes en momentos diferentes? –

Respuesta

2

De MSDN, utilizando la propiedad ProcessThread.ProcessorAffinity que pueda establecer la afinidad hilo, pero no puede conseguirlo. Por defecto, los subprocesos no tienen afinidad (pueden operar en cualquier procesador).

using System; 
using System.Diagnostics; 

namespace ProcessThreadIdealProcessor 
{ 
    class Program 
    { 
     static void Main(string[] args) 
     { 
      // Make sure there is an instance of notepad running. 
      Process[] notepads = Process.GetProcessesByName("notepad"); 
      if (notepads.Length == 0) 
       Process.Start("notepad"); 
      ProcessThreadCollection threads; 
      //Process[] notepads; 
      // Retrieve the Notepad processes. 
      notepads = Process.GetProcessesByName("Notepad"); 
      // Get the ProcessThread collection for the first instance 
      threads = notepads[0].Threads; 
      // Set the properties on the first ProcessThread in the collection 
      threads[0].IdealProcessor = 0; 
      threads[0].ProcessorAffinity = (IntPtr)1; 
     } 
    } 
} 

Similarmente, Thread.SetProcessorAffinity hace lo mismo.

+1

Además, se movieron los hilos, por lo que incluso si recibiera una respuesta, no sería necesariamente válida en el momento en que intentara verificar algo. – TomTom

+0

Sí, las propiedades ProcessorAffinity en Process y ProcessThread fueron mi primera esperanza, pero como usted señaló, no puedo OBTENER ... – Harald

+0

@TomTom: sí, se pueden mover, pero en nuestro caso una instantánea ya proporcionaría Información valiosa. – Harald

2

Esto no se puede hacer de manera continua y confiable. El programador de tareas del sistema operativo optimiza los hilos y divide la carga entre los núcleos de CPU disponibles. En general, un hilo se puede ejecutar en cualquier CPU. Además, con los cambios de contexto también puede cambiar su CPU.

Si necesita señalar un hilo o un proceso específico, solo puede asignar su afinidad, por lo que puede tener la esperanza razonable de que el proceso/hilo se ejecutará en una CPU lógica particular.

+0

Aunque técnicamente correcto, su respuesta le falta un punto muy importante. Saber que su CPU actual ** puede ** dramáticamente ** reducir la contención al dividir el recurso compartido. Sí, en casos excepcionales será interrumpido y trasladado a otro núcleo. Esto significa que la sincronización todavía es necesaria. Pero los resultados de perf son incomparables. –

+0

@KirillKobelev puede darme algunas referencias para esto. Puedo ver que funciona en un nivel bajo, pero no estoy seguro de cómo puede administrar esto desde una aplicación. ¿Estás hablando de NUMA? – oleksii

+0

Piense en el rendimiento de 'int cnt [num_cores]; InterlockedIncrement (cnt [GetCurrCore()]); 'versus versión simple con solo un contador. –

Cuestiones relacionadas