¿Verifica si HyperThreading está habilitado o no?

51

¿Cómo puedo verificar si hyperthreading está habilitado en una máquina Linux, usando un script perl para verificarlo?

Estoy intentando de la siguiente manera:

dmidecode -t processor | grep HTT

Avísame si estoy en el camino correcto.

De dos pisos
fuente
2
porque dmidecodetienes que ser root.
Nils
55
Me gusta cómo todos ignoraron el bit "script perl" ;-)
SamB
Esta debería ser la respuesta aceptada: unix.stackexchange.com/a/522295/1131
maxschlepzig

Respuestas:

27

Notas agregadas el 8 de julio de 2014: como señaló Riccardo Murri , mi respuesta a continuación solo muestra si el procesador informa que admite hyperthreading. Generalmente, * nix O / S están configurados para habilitar hyperthreading si es compatible. Sin embargo, para verificar esto mediante programación, vea, por ejemplo , la respuesta de Nils .

---- Respuesta original del 25 de marzo de 2012:

De hecho, estás en el camino correcto :) con

dmidecode -t processor | grep HTT

En Linux, generalmente busco "ht" en la línea "flags" de /proc/cpuinfo. Ver por ejemplo

grep '^flags\b' /proc/cpuinfo | tail -1

o si quieres incluir el "ht" en el patrón

grep -o '^flags\b.*: .*\bht\b' /proc/cpuinfo | tail -1

( \bcoincide con los límites de las palabras y ayuda a evitar falsos positivos en los casos en que "ht" es parte de otro indicador).

xebeche
fuente
19
Esto solo le dirá si el procesador es compatible con HT, no si realmente se está utilizando HT.
Riccardo Murri
3
el campo HTT no indica que el procesador realmente tenga hyperthreading en sus núcleos. comprobar el valor de 'hermanos' y 'CPU núcleos' en / proc / cpuinfo
Silver Moon
@ Silver-Moon ¿Puedes explicarlo? dmidecode lee el SMBIOS y debe indicar las capacidades del procesador. No indica si el O / S ve o utiliza el hiperprocesamiento. Pero esto ya ha sido comentado. Ver también la respuesta de Nils
xebeche
1
@xebeche en mi salida dmidecode del sistema muestra "HTT (Multi-threading)" pero mi procesador es "core 2 quad Q8400" que no tiene hyperthreading. Verifique las especificaciones de Intel.
Silver Moon
1
+1 a Riccardo; Tengo HT deshabilitado en un servidor con capacidad HT, y veo que imprime "HTT". lscpuEs la forma de comprobarlo.
sudo
96

Siempre usé lo siguiente y miré 'Hilo (s) por núcleo:'.

hostname:~ # lscpu
Architecture:          x86_64
CPU(s):                24
Thread(s) per core:    2                <-- here
Core(s) per socket:    6
CPU socket(s):         2
NUMA node(s):          2
Vendor ID:             GenuineIntel
CPU family:            6
Model:                 44
Stepping:              2
CPU MHz:               1596.000
Virtualization:        VT-x
L1d cache:             32K
L1i cache:             32K
L2 cache:              256K
L3 cache:              12288K

Sin embargo, tenga en cuenta que esta técnica fallará si algún procesador lógico se ha apagado con un simple

echo 0 > /sys/devices/system/cpu/cpuX/online
stephaniea
fuente
44
Esta es la mejor respuesta hasta ahora. No requiere la lectura de las hojas de té, mucha información útil y no requiere grepping.
MrMas
11
Dios mío, ¿usaste un comando de shell para obtener tu respuesta? Eso es tan de la vieja escuela -1 para eso. ¿Qué pasa con un buen script de Python? Solo te llevaría una tarde escribir. Como no es Python, otro -1. Pero +3 por brevedad.
Mike S
@Mike S mucho sarcasmo pero ... La salida de lscpu no es correcta cuando, por ejemplo, solo 1 núcleo hiperprocesado está inactivo en una CPU de 4 núcleos (que es un escenario completamente válido). Porque entonces informará "Thread (s) por core: 1" aunque 3 núcleos son en realidad hiperthreaded (7 hilos en total).
Cedric Martin
@Cedric Martin te diste cuenta. :-) ... Oooo! Buena captura ... lo hice! Tomó una máquina dual de 8 núcleos (CPU Dell R620 / E5-2667 v2) ... informa 32 CPU ... Realizado echo 0 > /sys/devices/system/cpu/cpu31/online, ahora informa lscpu Thread(s) per core: 1. Mal lscpu! Supongo que ya no usaré esto.
Mike S
3
@ Mike S Todavía puedes usar lscpu , pero supongo que no esa línea. Usando, digamos, "lscpu -e -a" enumera correctamente cada hilo y le dice si está activo o no. Es solo que "Thread (s) per core" no tiene mucho sentido cuando puede habilitar / deshabilitar hilos de manera diferente en cada núcleo.
Cedric Martin
18

Si la cantidad de procesadores lógicos es el doble de la cantidad de núcleos que tiene HT. Use el siguiente script para decodificar / proc / cpuinfo :

#!/bin/sh
CPUFILE=/proc/cpuinfo
test -f $CPUFILE || exit 1
NUMPHY=`grep "physical id" $CPUFILE | sort -u | wc -l`
NUMLOG=`grep "processor" $CPUFILE | wc -l`
if [ $NUMPHY -eq 1 ]
  then
    echo This system has one physical CPU,
  else
    echo This system has $NUMPHY physical CPUs,
fi
if [ $NUMLOG -gt 1 ]
  then
    echo and $NUMLOG logical CPUs.
    NUMCORE=`grep "core id" $CPUFILE | sort -u | wc -l`
    if [ $NUMCORE -gt 1 ]
      then
        echo For every physical CPU there are $NUMCORE cores.
    fi
  else
    echo and one logical CPU.
fi
echo -n The CPU is a `grep "model name" $CPUFILE | sort -u | cut -d : -f 2-`
echo " with`grep "cache size" $CPUFILE | sort -u | cut -d : -f 2-` cache"
Nils
fuente
Si $NUMCORE > $NUMLOGpodemos decir que hyperthreading está habilitado, ¿verdad? De hecho 2 * $NUMCORE = $NUMLOG, ¿esto es siempre cierto o algunas CPU pueden tener 4 veces más núcleos?
Tombart
@Tombart Actualmente HT es el factor 2. Me imagino que podría ser más en el futuro. Un núcleo se señala como físico. El número de núcleos por socket puede derivarse de hermanos.
Nils
Si tiene lscpudisponible, lscpuproporcionará la misma información junto con muchos metadatos adicionales y la salida de lscpues más fácil de analizar. pero esta solución funciona y solo usa /proc/cpuinfo.
Trevor Boyd Smith
8

Los ejemplos anteriores muestran si la CPU es capaz de HT, pero no si se está utilizando. El último método funciona, pero no los servidores de doble socket y las máquinas virtuales se probaron Xenserverdonde no muestra CPU física, ya que no hay ninguno.

Encontré que esta es la forma más fácil y menos codificada, que también funcionó en todos mis entornos de prueba. pero requiere bc.

echo "testing ################################### "

nproc=$(grep -i "processor" /proc/cpuinfo | sort -u | wc -l)

phycore=$(cat /proc/cpuinfo | egrep "core id|physical id" | tr -d "\n" | sed s/physical/\\nphysical/g | grep -v ^$ | sort | uniq | wc -l)

if [ -z "$(echo "$phycore *2" | bc | grep $nproc)" ]

then

echo "Does not look like you have HT Enabled"

if [ -z "$( dmidecode -t processor | grep HTT)" ]

 then

echo "HT is also not Possible on this server"

 else

echo "This server is HT Capable,  However it is Disabled"

fi

else

   echo "yay  HT Is working"

fi


echo "testing ################################### "

Creo que esto funcionará en todas las plataformas y le dirá si su CPU es capaz y si está habilitada. Puede ser un poco desordenado, aunque soy un principiante en los scripts. Probé con centos XENSERVER vm, Ubuntu y Openfiler (rpath)

usuario63814
fuente
Su guión podría simplificarse mucho con solo leer /sys/devices/system/cpu/smt/control. Ver también la respuesta de Oscar
maxschlepzig
6

Puede verificar la capacidad HT de la CPU con este comando

# grep ht /proc/cpuinfo

Puede enumerar la CPU física y lógica vista por Kernel con el siguiente comando:

# egrep -i "processor|physical id" /proc/cpuinfo

Ofrece esta salida en una CPU habilitada para HT de un solo núcleo:

processor   : 0
physical id : 0
processor   : 1
physical id : 0

Puedes leer el resultado así:

processor   : 0 (CPU 0, first logical)
physical id : 0 (CPU 0 is on the first physical)
processor   : 1 (CPU 1, second logical)
physical id : 0 (CPU 1 is on the first physical)
=> It means I have HT enabled
Coren
fuente
1
Esto solo le dirá si el procesador es compatible con HT, no si realmente se está utilizando HT. Los nodos cuyo procesador sea compatible con HT pero donde HT no esté habilitado seguirán publicitándose hten los indicadores de CPU.
Riccardo Murri
@RiccardoMurri Hasta donde yo sé, cuando HT está deshabilitado, el indicador ht no aparece en / proc / cpuinfo
Coren
66
Estoy bastante seguro de que no lo es. Tengo servidores habilitados para HT y HT deshabilitados, y todos ellos muestran la bandera ht.
Riccardo Murri
2
Si tiene un procesador Xeon con 4 núcleos, se mostrará como una identificación física y cuatro procesadores. Por lo tanto, puede tener múltiples procesadores por identificación física sin hipervínculos.
Andomar
2
Tengo una máquina de 2 zócalos, y physical idparece representar el zócalo / chip. El core idparece apuntar a un mismo núcleo físico
Heartinpiece
6

Este liner parece hacer el truco para mí (requiere privilegios de root):

dmidecode -t processor | grep -E '(Core Count|Thread Count)'

El resultado es:

Core Count: 2
Thread Count: 4

El recuento de subprocesos es el doble del recuento principal, por lo tanto, tengo hyperthreading habilitado.

O si realmente quieres tu script perl, como se solicitó ...

perl -e 'print grep(/Core Count/ || /Thread Count/, `dmidecode -t processor`);'
billyw
fuente
1
Tengo HT apagado en un sistema compatible con HT basado en Intel, sin embargo, Thread Count devuelto con dmidecode es dos veces el Core Count. Parece que muestra si la CPU es compatible con HT, no si HT está habilitado o no.
Dmitri Chubarov
@Dmitri Weird. Acabo de ejecutar esto en un servidor con capacidad HT (tiene dos Intel Xeon E5-2670 v3) con hyperthreading deshabilitado, y el recuento de núcleos e hilos era el mismo. No estoy seguro de qué causaría la diferencia en el comportamiento. Tendré que investigar más a fondo.
billyw
Acabo de ejecutar esto en un Dell R610 con dos procesadores X5680, Hyperthreading apagado, y el recuento de subprocesos es el doble del recuento de núcleos. La respuesta de stephaniea (lscpu) parece funcionar. He verificado dos veces el iDRAC (el procesador fuera de banda de Dell sin luz [para aquellos que no lo saben]) y dice que Hyperthreading está apagado. Entonces no creo que dmidecodesea ​​confiable.
Mike S
Revisé una Dell 1950 (CPU x5460, no es posible el hyperthreading) y lscpu era correcto. También un Dell R620 (E5-2690 [v1, creo]) y fue correcto.
Mike S
Pero el comentario de @Cedric Martin en una de las respuestas anteriores muestra que lscpuno siempre será confiable. Me gusta la respuesta de scottbb.
Mike S
3
perl -ne'
  $i++ if /^\s*$/;
  push @{$x[$i]}, [/^(.+?) \s*:\s* (.+)/x] if /core|sibling|physical id/; }{
  $r= shift @x; 
  for $i (0..$#$r) {
    $$r[$i][1] .= " ".$$_[$i][1] for @x;
    printf "%-15s: %s\n", @{$$r[$i]};
  }
' /proc/cpuinfo

Este resultado indica que HT está habilitado ya que el siblingsnúmero (12) es mayor que cpu cores(6)

physical id    : 0 0 0 0 0 0 1 1 1 1 1 1 0 0 0 0 0 0 1 1 1 1 1 1
siblings       : 12 12 12 12 12 12 12 12 12 12 12 12 12 12 12 12 12 12 12 12 12 12 12 12
core id        : 0 1 2 8 9 10 0 1 2 8 9 10 0 1 2 8 9 10 0 1 2 8 9 10
cpu cores      : 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6 6
mpapec
fuente
2

Si lee /sys/devices/system/cpu/cpu0/topology/thread_siblings_list, devolverá una lista separada por comas de los hermanos de subproceso (es decir, "núcleos" de Hyperthread) de la CPU 0.

Por ejemplo, en mi Xeon de 2 sockets y 6 núcleos, con hyperthreading habilitado obtengo:

cat /sys/devices/system/cpu/cpu0/topology/thread_siblings_list
0,12

Pero después de desactivar hyperthreading en BIOS, obtengo:

cat /sys/devices/system/cpu/cpu0/topology/thread_siblings_list
0

Suponiendo que la CPU 0 siempre estará disponible, luego verificar el thread_sibling_listarchivo procfs de la CPU 0 para más de un nodo, o buscar una coma, o incluso cualquier otra cosa 0, indicará si hyperthreading está habilitado.


Yo respondería en Perl, pero 1) No lo sé, y 2) Supongo que la solución es bastante trivial.

scottbb
fuente
2

En Linux esto funciona bien:

$ lscpu -e  
CPU NODE SOCKET CORE L1d:L1i:L2:L3 ONLINE  
0   0    0      0    0:0:0:0       yes  
1   0    0      1    1:1:1:0       yes  
2   0    0      2    2:2:2:0       yes  
3   0    0      3    3:3:3:0       yes  
4   0    0      4    4:4:4:0       yes  
5   0    0      5    5:5:5:0       yes  
6   0    0      6    6:6:6:0       yes  
7   0    0      7    7:7:7:0       yes  
8   1    1      8    8:8:8:1       yes  
9   1    1      9    9:9:9:1       yes  
10  1    1      10   10:10:10:1    yes  
11  1    1      11   11:11:11:1    yes  
12  1    1      12   12:12:12:1    yes  
13  1    1      13   13:13:13:1    yes  
14  1    1      14   14:14:14:1    yes  
15  1    1      15   15:15:15:1    yes  
16  0    0      0    0:0:0:0       yes  
17  0    0      1    1:1:1:0       yes   
18  0    0      2    2:2:2:0       yes  
19  0    0      3    3:3:3:0       yes  
20  0    0      4    4:4:4:0       yes  
21  0    0      5    5:5:5:0       yes  
22  0    0      6    6:6:6:0       yes  
23  0    0      7    7:7:7:0       yes  
24  1    1      8    8:8:8:1       yes  
25  1    1      9    9:9:9:1       yes  
26  1    1      10   10:10:10:1    yes  
27  1    1      11   11:11:11:1    yes  
28  1    1      12   12:12:12:1    yes  
29  1    1      13   13:13:13:1    yes  
30  1    1      14   14:14:14:1    yes  
31  1    1      15   15:15:15:1    yes  

En el ejemplo anterior, tenemos 2 sockets NUMA (SOCKET = 1 o 2). Tenemos 16 núcleos físicos (CORE = 0 a 15). Cada CORE tiene un hyperthread hermano (por ejemplo CORE = 0 contiene CPU 0,16.

Podemos verificar el hyperthread así:

$ cat /sys/devices/system/cpu/cpu0/topology/thread_siblings_list  
0,16

La jerarquía de la memoria caché es:

CPU 0 --> L1D_0|L1I_0 -> L2_0 -> L3_0  
          ^                      ^
CPU 16 ---|                      |     
                                 |         
CPU 1 --> L1D_1|L1I_1 -> L2_1 ---> 
          ^    
CPU 17 ---|   
...    

lscpu -p proporciona una salida en formato csv para analizar fácilmente el programa.

$ lscpu -p  
# The following is the parsable format, which can be fed to other
# programs. Each different item in every column has an unique ID
# starting from zero.
# CPU,Core,Socket,Node,,L1d,L1i,L2,L3
0,0,0,0,,0,0,0,0
1,1,0,0,,1,1,1,0
2,2,0,0,,2,2,2,0
3,3,0,0,,3,3,3,0
4,4,0,0,,4,4,4,0
...
edW
fuente
2

Aquí hay un enfoque basado en Python: también sugiere formas de deshabilitarlo si es necesario.

import re    

total_logical_cpus = 0
total_physical_cpus = 0
total_cores = 0

logical_cpus = {}
physical_cpus = {}
cores = {}

hyperthreading = False

for line in open('/proc/cpuinfo').readlines():
    if re.match('processor', line):
        cpu = int(line.split()[2])

        if cpu not in logical_cpus:
            logical_cpus[cpu] = []
            total_logical_cpus += 1

    if re.match('physical id', line):
        phys_id = int(line.split()[3])

        if phys_id not in physical_cpus:
            physical_cpus[phys_id] = []
            total_physical_cpus += 1

    if re.match('core id', line):
        core = int(line.split()[3])

        if core not in cores:
            cores[core] = []
            total_cores += 1

        cores[core].append(cpu)

if (total_cores * total_physical_cpus) * 2 == total_logical_cpus:
    hyperthreading = True

print("  This system has %d physical CPUs" % total_physical_cpus)
print("  This system has %d cores per physical CPU" % total_cores)
print("  This system has %d total cores" % (total_cores * total_physical_cpus))
print("  This system has %d logical CPUs" % total_logical_cpus)

if hyperthreading:
    print("  HT detected, if you want to disable it:")
    print("  Edit your grub config and add 'noht'")
    print("  -OR- disable hyperthreading in the BIOS")
    print("  -OR- try the following to offline those CPUs:")

    for c in cores:
        for p, val in enumerate(cores[c]):
            if p > 0:
                print("    echo 0 > /sys/devices/system/cpu/cpu%d/online" % (val))
Neil McGill
fuente
La sugerencia para deshabilitar hyperthreading es subóptima: la forma directa de deshabilitar hyperthreading es echo off > /sys/devices/system/cpu/smt/control(además de desactivarlo en la BIOS). Ver también la respuesta de Oscar para una verificación directa.
maxschlepzig
1

Hay muchas advertencias y qué pasa si está en las respuestas aquí ... parece que la respuesta no es tan obvia. lscputiene su gotcha, que se aplica a cualquier "núcleo de conteo y procesadores lógicos, luego compara" la respuesta. Debido a que puede apagar los procesadores lógicos con un simple comando de eco (... esto podría ser crítico en un entorno empresarial grande donde depende del modo turbo, por ejemplo).

Aquí está mi intento; Gracias a @scottbb por la inspiración:

printf "HT is "; egrep -q [:punct:] /sys/devices/system/cpu/cpu0/topology/thread_siblings_list && echo on || echo off 

En mis máquinas basadas en Dell Xeon, la lista de hermanos incluye una coma cuando HT está activado. En mi computadora portátil, incluye un guión (procesador i5-3210m). Así que estoy preparando para la puntuación.

Pensamientos? ¿Críticas?

El solicitante pidió perl, así que aquí tienes:

perl -ane 'chomp; print "Hyperthreading is "; if (/\D/) { print "ON\n" } else { print "OFF\n" }' < /sys/devices/system/cpu/cpu0/topology/thread_siblings_list
Mike S
fuente
Solo lo usaría, grep -q [-.]ya que esto es menos para escribir. FWIW, he comprobado varios Xeons / i5 / i7 (incluidas las variantes móviles) y ninguno de ellos tiene un guión en el thread_siblings_list. No es suficiente para simplemente cpu0 cheque - por lo tanto, algo como esto sería más robusto: grep -q , /sys/devices/system/cpu/cpu*/topology/thread_siblings_list. Sin embargo, solo a grep 1 /sys/devices/system/cpu/smt/active -qes aún más importante: cf. La respuesta de Oscar
maxschlepzig
1

La forma más fácil de verificar si SMT (genérico para HT, que es solo la marca Intel) está activo, simplemente haga:

cat /sys/devices/system/cpu/smt/active

le da 0 para inactivo o 1 para activo

En realidad, puede activarlo o desactivarlo en tiempo de ejecución con:

echo [on|off] > /sys/devices/system/cpu/smt/control
Oscar Tiderman
fuente
La captura también/sys/devices/system/cpu/smt/control es posible y rinde on|off|forceoff|notsupported|notimplemented.
maxschlepzig
0

Mejor verifique lscpu, donde puede ver "Thread (s) por core: 1", significa solo un thread por 1 core.

    # lscpu
    Architecture:          x86_64
    CPU op-mode(s):        32-bit, 64-bit
    Byte Order:            Little Endian

CPU(s):                8
On-line CPU(s) list:   0-7
Thread(s) per core:    1
Core(s) per socket:    4
Socket(s):             2
NUMA node(s):          2
Vendor ID:             GenuineIntel
CPU family:            6
Model:                 63
Model name:            Intel(R) Xeon(R) CPU E5-2623 v3 @ 3.00GHz
Stepping:              2
CPU MHz:               1200.000
BogoMIPS:              5992.82
Virtualization:        VT-x
L1d cache:             32K
L1i cache:             32K
L2 cache:              256K
L3 cache:              10240K
NUMA node0 CPU(s):     0,1,4,5
NUMA node1 CPU(s):     2,3,6,7
Gineesh
fuente
0

Stephaniea ya lo ha mencionado lscpu. Quería agregar un poco más a eso.

En mi procesador AMD Epyc, cada vez que hay un núcleo lógico fuera de línea, lscpumuestra una nueva línea adicional llamadaOff-line CPU(s) list:

# echo 0 > /sys/devices/system/cpu/cpu9/online
# echo 0 > /sys/devices/system/cpu/cpu16/online
# 
#lscpu
CPU(s):                64
On-line CPU(s) list:   0-8,10-15,17-63
Off-line CPU(s) list:  9,16
talekeDskobeDa
fuente