Disabilita l'hyper threading in Ubuntu


14

Sto eseguendo il server Ubuntu 16.04. Vedo che il threading hype è abilitato quando utilizzo il comando lscpu.

Voglio disabilitarlo. Ho visitato i forum di Ubuntu e qui e qui .

Queste sono buone discussioni sul perché l'hyper threading potrebbe non essere buono. Ma nessuna soluzione definitiva su come disattivarlo.

Qualcuno può dare i passaggi per disabilitare l'hyperthreading? Grazie .


3
Hai provato a disabilitarlo nel BIOS?
edwinksl,

sì, non è stato possibile trovare un'opzione per HT
john

Risposte:


9

introduzione

Questa è una domanda interessante Probabilmente uno dei più interessanti da mesi per me personalmente. Come l'OP non esiste alcuna opzione per disabilitare Hyper Threading nel mio vecchio BIOS (inventato nel 2012, aggiornato nel 2016 o giù di lì).

Bug Hyper-Threading in Intel Skylake e Kaby Lake:

Chiunque utilizzi processori Intel Skylake o Kaby Lake deve leggere le segnalazioni di bug relative a Hyper Threading emerse un paio di mesi fa. Questa storia del Registro del Regno Unito spiega come gli sviluppatori Debian hanno notato come Hyper Threading può arrestare e danneggiare la macchina.

Ci sono numerosi problemi con Skylake riportati in Ask Ubuntu nell'ultimo anno e ci si chiede come discernere quali problemi potrebbero essere stati causati dai bug di Hyper Threading.

Questa risposta è divisa in tre parti:

  • Visualizzazione delle CPU quando Hyper-Threading è disattivato / attivato
  • Script di Bash per automatizzare l'attivazione / disattivazione dell'hyper-threading
  • Conky si blocca se Hyper Threading è disattivato prima che inizi

Visualizzazione delle CPU quando Hyper-Threading è disattivato / attivato

Di seguito è possibile visualizzare l'utilizzo della CPU quando l'hyper-threading è disattivato e viene eseguito uno stress test della CPU. Circa 10 secondi dopo lo stesso script viene ripetuto con l'hyper threading attivato. Finalmente 10 secondi dopo che lo script viene eseguito con l'hyper-threading disattivato di nuovo:

Imposta n. Hyper threading

Il display è diviso in due sezioni:

  • Sulla metà sinistra della finestra del terminale invoca lo script set-hyper-threadingcon il parametro 0 (off) e quindi 1 (on).
  • Nella metà destra conkyviene visualizzato l'utilizzo percentuale CPU di CPUS da 1 a 8.

Il primo script esegue Hyper Threading

La prima volta che viene eseguito lo script, i numeri CPU 2, 4, 6 e 8 (secondo Conky) vengono congelati al 3%, 2%, 2% e 2%. I numeri CPU 1, 3, 5 e 7 aumentano al 100% mentre viene eseguito lo stress test.

La topologia della CPU viene visualizzata con l'hyper-threading disattivato e vengono riportati solo i quattro core:

/sys/devices/system/cpu/cpu0/topology/core_id:0
/sys/devices/system/cpu/cpu2/topology/core_id:1
/sys/devices/system/cpu/cpu4/topology/core_id:2
/sys/devices/system/cpu/cpu6/topology/core_id:3

Il secondo script esegue Hyper Threading

La seconda volta che viene eseguito lo script Hyper-Threading viene attivato e tutti i numeri di CPU 1-8 aumentano al 100% mentre viene eseguito lo stress test.

La topologia della CPU viene visualizzata con l'hyper-threading attivato e vengono riportati solo i quattro core plus e quattro core virtuali:

/sys/devices/system/cpu/cpu0/topology/core_id:0
/sys/devices/system/cpu/cpu1/topology/core_id:0
/sys/devices/system/cpu/cpu2/topology/core_id:1
/sys/devices/system/cpu/cpu3/topology/core_id:1
/sys/devices/system/cpu/cpu4/topology/core_id:2
/sys/devices/system/cpu/cpu5/topology/core_id:2
/sys/devices/system/cpu/cpu6/topology/core_id:3
/sys/devices/system/cpu/cpu7/topology/core_id:3

Il terzo script esegue Hyper Threading

Nota come dopo la fine del secondo script le CPU 2, 4, 6 e 8 sono inattive al 4%, 2%, 3%, 4%. Ciò è importante perché nel terzo test la disattivazione di Hyper-Threading mostra le percentuali di CPU bloccate al 4%, 2%, 3%, 4% anziché 3%, 2%, 2% e 2% dal primo test.

Pertanto, disattivare l'hyper-threading sembra bloccare le CPU virtuali allo stato corrente.

Nota anche se si attiva o disattiva Hyper-Threading lo script visualizza ancora "Hyper-Threading supportato".


Script di Bash per automatizzare l'attivazione / disattivazione dell'hyper-threading

Quando si visualizza lo script seguente, tenere presente che Conky numera le CPU da 1 a 8 ma Linux numera le CPU da 0 a 7.

#!/bin/bash

# NAME: set-hyper-threading
# PATH: /usr/local/bin
# DESC: Turn Hyper threading off or on.

# DATE: Aug. 5, 2017.

# NOTE: Written Part of testing for Ubuntu answer:
#       /ubuntu/942728/disable-hyper-threading-in-ubuntu/942843#942843

# PARM: 1="0" turn off hyper threading, "1" turn it on.

if [[ $# -ne 1 ]]; then
    echo 'One argument required. 0 to turn off hyper-threading or'
    echo '1 to turn hyper-threading back on'
    exit 1
fi

echo $1 > /sys/devices/system/cpu/cpu1/online
echo $1 > /sys/devices/system/cpu/cpu3/online
echo $1 > /sys/devices/system/cpu/cpu5/online
echo $1 > /sys/devices/system/cpu/cpu7/online

grep "" /sys/devices/system/cpu/cpu*/topology/core_id

grep -q '^flags.*[[:space:]]ht[[:space:]]' /proc/cpuinfo && \
    echo "Hyper-threading is supported"

grep -E 'model|stepping' /proc/cpuinfo | sort -u

stress --cpu 8 --io 1 --vm 1 --vm-bytes 128M --timeout 10s

NOTA: il programma stressè integrato in tutti i sistemi Debian di cui Ubuntu è un derivato. Pertanto non è necessario scaricare e installare alcun pacchetto per eseguire questo script in Ubuntu.

Se hai una CPU dual core devi rimuovere (o commentare con #) le linee che controllano i numeri CPU 5 e 7.

Ringraziamo Hi-Angel per la riga bash che grep "" /sys/devices/system/cpu/cpu*/topology/core_idmostra la topologia della CPU.


Conky si blocca se Hyper Threading è disattivato prima che inizi

Per ottenere CPU dal 2, 4, 6, 8 all'utilizzo percentuale più basso possibile, ho provato a disattivare Hyper-Threading durante l'avvio. Ho usato questo script per farlo:

# NAME: /etc/cron.d/turn-off-hyper-threading
# DATE: Auguust 5, 1017
# DESC: This turns off CPU 1, 3, 5 & 7
# NOTE: Part of testing for Ubuntu answer:
#       /ubuntu/942728/disable-hyper-threading-in-ubuntu/942843#942843
# BUGS: Conky crashes with Segmentation Fault when CPU 2,4,6 & 8 (as conky calls them)
#       are off-line.
#
SHELL=/bin/sh
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
#
# @reboot   root    echo 0 > /sys/devices/system/cpu/cpu1/online
# @reboot   root    echo 0 > /sys/devices/system/cpu/cpu3/online
# @reboot   root    echo 0 > /sys/devices/system/cpu/cpu5/online
# @reboot   root    echo 0 > /sys/devices/system/cpu/cpu7/online

Tuttavia si conkyarresta in modo anomalo con un errore di segmentazione se l'hyper-threading è disattivato all'avvio. Come tale ho dovuto commentare le quattro @rebootrighe della sceneggiatura.

Codice Conky per visualizzare l'utilizzo percentuale CPU e il fattore di carico

Se sei interessato a configurare un display simile in Conky, ecco lo snippet di codice pertinente:

${color orange}${voffset 2}${hr 1}
${color2}${voffset 5}Intel® i-7 3630QM 3.4 GHz: ${color1}@  ${color green}${freq} MHz   
${color}${goto 13}CPU 1 ${goto 81}${color green}${cpu cpu1}% ${goto 131}${color3}${cpubar cpu1 18}
${color}${goto 13}CPU 2 ${goto 81}${color green}${cpu cpu2}% ${goto 131}${color3}${cpubar cpu2 18}
${color}${goto 13}CPU 3 ${goto 81}${color green}${cpu cpu3}% ${goto 131}${color3}${cpubar cpu3 18}
${color}${goto 13}CPU 4 ${goto 81}${color green}${cpu cpu4}% ${goto 131}${color3}${cpubar cpu4 18}
${color}${goto 13}CPU 5 ${goto 81}${color green}${cpu cpu5}% ${goto 131}${color3}${cpubar cpu5 18}
${color}${goto 13}CPU 6 ${goto 81}${color green}${cpu cpu6}% ${goto 131}${color3}${cpubar cpu6 18}
${color}${goto 13}CPU 7 ${goto 81}${color green}${cpu cpu7}% ${goto 131}${color3}${cpubar cpu7 18}
${color}${goto 13}CPU 8 ${goto 81}${color green}${cpu cpu8}% ${goto 131}${color3}${cpubar cpu8 18}
${color1}All CPU ${color green}${cpu}% ${goto 131}${color1}Temp: ${color green}${hwmon 2 temp 1}°C ${goto 250}${color1}Up: ${color green}$uptime
${color green}$running_processes ${color1}running of ${color green}$processes ${color1}loaded processes.
Load Avg. 1-5-15 minutes: ${alignr}${color green}${execpi .001 (awk '{printf "%s/", $1}' /proc/loadavg; grep -c processor /proc/cpuinfo;) | bc -l | cut -c1-4} ${execpi .001 (awk '{printf "%s/", $2}' /proc/loadavg; grep -c processor /proc/cpuinfo;) | bc -l | cut -c1-4} ${execpi .001 (awk '{printf "%s/", $3}' /proc/loadavg; grep -c processor /proc/cpuinfo;) | bc -l | cut -c1-4}
${color1}NVIDIA  ${color}-GPU ${color green}${nvidia gpufreq} Mhz  ${color}-Memory ${color green}${nvidia memfreq} Mhz
${color1}GT650M ${color}-Temp ${color green}${nvidia temp}°C  ${color}-Threshold ${color green}${nvidia threshold}°C
${color orange}${voffset 2}${hr 1}

NOTA: il codice Nvidia sopra non è mai stato testato perché la GPU Nvidia non funziona ancora con Ubuntu. Ogni anno presto ora :)


1
Siamo spiacenti, ma nohtnon esiste. Ho anche cercato l'opzione attraverso fonti linux-4.13-rc1 che mi capita di avere occasionalmente. Tuttavia, certamente capisco cosa potrebbe averti confuso: dat bugreport si lamenta che l'opzione non funziona, e quindi viene chiusa come nextrelease, come se avessero risolto qualcosa. Tuttavia, se leggi i commenti, vedrai che l'unico uso di nohtè per uno script fatto a mano che controlla la riga di comando del kernel per l'opzione, quindi disabilita i core attraverso il /sys/filesystem. IOW nohtè inutile.
Ciao Angelo

@ Ciao Angelo Grazie per aver sottolineato che non è necessario. Ho fatto i test senza di essa e i core off-line sono raddoppiati dal 2,2,5,5% (senza valore) al 5,5,10,10% (senza valore). Farò altri test stasera. Ho cercato la documentazione dei parametri del kernel e non sono riuscito a trovare alcun riferimento noht.
WinEunuuchs2Unix

Sulla nota a margine , non c'è linguaggio macchina / umano da indicizzare :) Per risolvere la confusione con indici a partire da 0, 1 o anche un numero particolare (come in MiniZinc) , è meglio pensare in termini di set di indici , ovvero suriezione da un insieme di indici a un altro insieme. L'astrazione via consente di notare più facilmente quando alcuni elementi rilevanti per un dato di dati, che non rappresentano gli indici, possono effettivamente essere utilizzati per l'indicizzazione dopo essere stato leggermente modificato. Il vantaggio deriva dall'avere in mente un concetto non associato a un layout di memoria e altre limitazioni.
Ciao Angelo

@ Hi-Angel Confronto simile tra "Posizione iniziale" e "Offset" credo. Comunque sto per riscrivere questa risposta sulla base degli ultimi due giorni di test e codifica, così i nostri commenti saranno presto obsoleti ...
WinEunuuchs2Unix

6

I kernel recenti supportano il parametro kernel maxcpus .

Ciò consente di impostare il numero di cpus sul numero di core fisici. Questo può essere utile per aiutare a mitigare le minacce causate dalle vulnerabilità MDS sulle CPU Intel della famiglia 6.

Come:

con i privilegi di sudo (root) apri / etc / default / grub con il tuo editor di testo preferito.

Trova la riga che inizia con GRUB_CMDLINE_LINUX_DEFAULT =

e aggiungi maxcpus = n a tutti i parametri del kernel esistenti come i parametri di quiet splash comuni (dove n = il numero di core fisici della tua cpu.

Ad esempio sul mio fidato processore Intel (R) Core (TM) i3-3220 CPU @ 3.30GHz dual core con hyperthreading ho aggiunto maxcpus = 2 per disattivare l'hyperthreading all'avvio.

Salvare il file, quindi immettere il comando sudo update-grube riavviare.

Puoi confermare il successo emettendo il comando lscpu | grep "per core"che dovrebbe fornire un output come questo:

Thread(s) per core: 1

Testato sul kernel 4.4.0

fonti:

https://github.com/torvalds/linux/blob/master/Documentation/admin-guide/kernel-parameters.txt

https://www.kernel.org/doc/html/latest/admin-guide/hw-vuln/mds.html

/unix/145645/disabling-cpu-cores-on-quad-core-processor-on-linux


1
Link interessanti. Grazie per la condivisione.
WinEunuuchs2Unix

@ WinEunuuchs2Unix Il mio piacere. Sempre desideroso di aiutare!
Elder Geek,

4

Puoi disabilitare l'hyperthreading in Linux come root o con i privilegi di superutente con:

# echo off > /sys/devices/system/cpu/smt/control

È possibile visualizzare lo stato di hyperthreading corrente con:

$ cat /sys/devices/system/cpu/smt/control

Questo comando stampa uno dei seguenti:

on|off|forceoff|notsupported|notimplemented

In alternativa, la maggior parte dei firmware BIOS include anche un'opzione per disabilitare l'hyperthreading. Se è disabilitato nel BIOS, probabilmente il gatto sopra riportato ritorna forceoff.


Hai provato questo per disabilitare l'hyper threading all'avvio?
Elder Geek,

1
@ElderGeek no, non ho provato il maxcpus=parametro del kernel per disabilitare l'hyperthreading. Principalmente perché non riesco a trovare alcuna documentazione ufficiale sulla sua interazione con i core hyperthreading. È garantito disabilitare sempre l'hyperthreading se si specifica maxcpus=#real_cores? O potresti finire con metà dei core reali con HT ancora abilitato su alcuni sistemi? Inoltre, maxcpus=un'impostazione non è portatile tra macchine con conteggi core diversi. Mantenere le variazioni di questo parametro per macchine diverse sarebbe noioso e soggetto a errori.
maxschlepzig,

Nella mia esperienza ho sempre disabilitato l'hyperthreading se specifichi maxcpus = # real_cores purché tu ti fidi dell'output di lscpu | grep "per core"fai un punto vaild riguardo alla portabilità, tuttavia sul lato opposto l'impostazione del parametro del kernel una volta non sembra un'attività troppo onerosa per me.
Elder Geek,

2

Ecco uno script per identificare i core ht e attivarli online / offline.

#!/bin/bash
typeset -i core_id
typeset -i sibling_id
typeset -i state

for i in /sys/devices/system/cpu/cpu[0-9]*; do
  core_id="${i##*cpu}"
  sibling_id="-1"

  if [ -f ${i}/topology/thread_siblings_list ]; then
    sibling_id="$(cut -d',' -f1 ${i}/topology/thread_siblings_list)"
  fi

  if [ $core_id -ne $sibling_id ]; then
    state="$(<${i}/online)"
    echo -n "$((1-state))" > "${i}/online"
    echo "switched ${i}/online to $((1-state))"
  fi
done

@ WinEunuuchs2Unix , forse puoi aggiungerlo alla tua eccellente risposta.


Ho dovuto ordinare numericamente l'elenco per farlo funzionare correttamente:for i in $(find /sys/devices/system/cpu/cpu[0-9]* -maxdepth 0 -type d |sort -V); do
neuhaus

2

Il maxcpus=nparametro in GRUB_CMDLINE_LINUX_DEFAULT=non funziona correttamente. Mi ha lasciato con 2 core e 4 thread invece di 4 core 4 thread.

Ho trovato una soluzione

Aggiungi mitigations=auto,nosmta GRUB_CMDLINE_LINUX_DEFAULT=invece

Testato su Ubuntu 16.04 LTS con Linux 4.4.0.

Fonte: https://wiki.ubuntu.com/SecurityTeam/KnowledgeBase/MDS


1

È necessario un modo leggermente più solido di cercare nel kernel le coppie hyperthread per i sistemi in cui la scheda madre ospita più socket della CPU perché core_id è duplicato. Ecco la mia versione su un sistema con due chip Xeon a 8 core (esempio da Ubuntu 16.04):

$ cat /sys/devices/system/cpu/cpu*/topology/thread_siblings_list \
> | sort --unique --numeric-sort
0,16
1,17
2,18
3,19
4,20
5,21
6,22
7,23
8,24
9,25
10,26
11,27
12,28
13,29
14,30
15,31

Per vari scopi, potresti anche voler guardare nei file

/sys/devices/system/cpu/present
/sys/devices/system/cpu/online
/sys/devices/system/cpu/offline

0

Se hai letto discussioni, probabilmente sai che di solito è irragionevole disabilitare, quindi suppongo che lo desideri per scopi di apprendimento.

L'idea di HT è avere più set di registri CPU per ogni core fisico (i cosiddetti core virtuali) . Non esiste un core virtuale "migliore", sono identici. Grazie a questa conoscenza è possibile disabilitare i core virtuali tranne uno per ogni fisico.

Per prima cosa vuoi sapere quale coppia di core virtuali appartiene a quale core fisico nel /sys/filesystem. È possibile utilizzare il core_idfile per questo:

λ grep "" /sys/devices/system/cpu/cpu*/topology/core_id
/sys/devices/system/cpu/cpu0/topology/core_id:0
/sys/devices/system/cpu/cpu1/topology/core_id:2
/sys/devices/system/cpu/cpu2/topology/core_id:0
/sys/devices/system/cpu/cpu3/topology/core_id:2

Dall'output si può dedurre che cpu0 + cpu2 sono contenuti in un nucleo fisico e cpu1 + cpu3 nell'altro. Ora eleva i privilegi e usa il echocomando per disabilitarne uno in ogni coppia:

λ sudo -s
# echo 0 > /sys/devices/system/cpu/cpu1/online
# echo 0 > /sys/devices/system/cpu/cpu2/online

Nota che cpu0 non ha file "online" e non può essere disabilitato, quindi ho disabilitato cpu2.


0

La risposta di @ visit1985 non funziona se il separatore in thread_siblings_list non è una virgola (che è, ad esempio, il caso sul mio sistema AMD Ryzen).

Ecco uno script per disattivare l'hyper-threading che funziona con qualsiasi separatore:

#!/bin/bash

for cpu in /sys/devices/system/cpu/cpu[1-9]*; do
    if [ -e "$cpu/topology/thread_siblings_list" ]; then
        sibling=$(awk -F '[^0-9]' '{ print $2 }' $cpu/topology/thread_siblings_list)
        if [ ! -z $sibling ]; then
            echo 0 > "/sys/devices/system/cpu/cpu$sibling/online"
        fi
    fi
done

Ed eccone uno per attivare l'hyper-threading:

#!/bin/bash

for cpu in /sys/devices/system/cpu/cpu[1-9]*; do
    echo 1 > "$cpu/online"
done

Questo metodo funziona sulla tua CPU Ryzen?
Elder Geek,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.