Hyperthreading'i Linux içinden devre dışı bırakın (BIOS'a erişim yok)


26

Uzak bir tesiste finansal alım satım uygulaması yapan bir sistemim var. ILO / DRAC'ye erişimim yok, ancak aşırı köprüyü devre dışı bırakmam gerekiyor. Sistem Intel Westmere 3.33GHz X5680 altı çekirdekli işlemcileri çalıştırıyor. Yeniden başlatabilirim, ancak performans sorunları nedeniyle sistemin aşırı tarama özelliğini etkinleştirmediğinden emin olmak istiyorum. Bunu Linux içinden yapmanın temiz bir yolu var mı?

Düzenleme: nohtÇekirdek önyükleme komut satırına eklenen yönerge çalışmadı. RHEL için aynı.

Bkz .: https://bugzilla.redhat.com/show_bug.cgi?id=440321#c9

Yanıtlar:


21

İsterseniz bunu çalışma zamanında yapabilirsiniz. Burada açıklanan güzel bir çözüm buldum: http://www.absolutelytech.com/2011/08/01/how-to-disable-cpu-cores-in-linux/

Adım 1: Kapatmak istediğiniz linux işlemcileri tanımlayın:

cat /proc/cpuinfo

Aynı "çekirdek kimliğe" sahip CPU'ları arayın, her bir çiftten birini kapatmak istiyorsunuz.

Adım 2: Hiper işleyen CPU'ları kapatın (benim durumumda Linux tarafından görülen toplam 8 "CPU" nun son dördü)

echo 0 > /sys/devices/system/cpu/cpu4/online
echo 0 > /sys/devices/system/cpu/cpu5/online
echo 0 > /sys/devices/system/cpu/cpu6/online
echo 0 > /sys/devices/system/cpu/cpu7/online

Sistem başladıktan hemen sonra çalıştırdığınız bir komut dosyasını kendiniz ayarlayabilirsiniz.


1
Neredeyse beklediğim gibi çalışıyor . sanal çekirdekler devre dışı bırakıldı, şimdi cpu kullanan bir iş parçacığı çalıştırdığımda fiziksel çekirdeği% 100 yüklüyor. Ancak sysbench --num-threads=1 --test=cpu run, farklı num-thread'lerle ve HT açılıp kapatıldığında, HT'nin devre dışı bırakılmasının, birçok iş parçacığı olduğunda perfüzyonu azalttığını ve sadece bir iş parçacığı olsa bile, HT'yi kapatmanın bir faydası olmadığını söylüyor. Bu yüzden onu olduğu gibi bırakmanızı öneririm: en uygunudur.
Sergey P. aka azure,

Onları tekrar açma komutunun ne olduğunu biliyor musunuz? Cevabınızın başındaki bağlantı öldü ~. Teşekkürler!
user189035

@ user189035: echo 1yerine echo 0onları yeniden açmalısınız .
Peter Cordes

@ SergeyP.akaazure, bir finansal hizmetler uygulaması için HT'yi kapatmanın asıl nedeninin performans değil güvenlik olduğunu düşünüyorum.
Simon Richter

@SimonRichter Bu soru başlangıçta yazıldığı zaman, gerçekten performans oldu. SMT / HT, o dönemin işlemcilerindeki bazı iş yüklerinde neredeyse hiç iyi değildi. Meltdown / Spectre olayı ve daha yeni Foreshadow saldırıları yıllar sonra gerçekleşti.
Michael Hampton

14

Makine başlangıcında hyperthreading özelliğini devre dışı bırakmak için bir komut dosyası ...

Hyperthreading'i devre dışı bırakmak için, /etc/rc.local makinesinde bir komut dosyası içerir. Tamamen temiz değildir, ancak cpu mimarisinden bağımsız olarak kurulumu kolaydır ve herhangi bir modern linux dağıtımı üzerinde çalışmalıdır.

nano /etc/rc.local

    # place this near the end before the "exit 0"

    for CPU in /sys/devices/system/cpu/cpu[0-9]*; do
        CPUID=$(basename $CPU)
        echo "CPU: $CPUID";
        if test -e $CPU/online; then
                echo "1" > $CPU/online; 
        fi;
        COREID="$(cat $CPU/topology/core_id)";
        eval "COREENABLE=\"\${core${COREID}enable}\"";
        if ${COREENABLE:-true}; then        
                echo "${CPU} core=${CORE} -> enable"
                eval "core${COREID}enable='false'";
        else
                echo "$CPU core=${CORE} -> disable"; 
                echo "0" > "$CPU/online"; 
        fi; 
    done;    

Bu nasıl çalışıyor?

Linux çekirdeği bilgisi ve kontrollerine modern linux dağıtımlarında / sys dizinindeki dosyalar olarak erişilebilir. Örneğin:

/ sys / devices / system / cpu / cpu3 , çekirdek bilgilerini ve mantıksal CPU 3 için kontrolleri içerir.

cat / sys / devices / system / cpu / cpu3 / topoloji / core_id bu mantıksal CPU'nun ait olduğu temel sayıyı gösterecektir.

echo "0"> / sys / devices / system / cpu / cpu3 / online mantıksal cpu 3'ü kapatmanıza izin verir.

Neden çalışıyor?

Tam olarak nedenini bilmiyorum ... ancak sistem aşırı tarama ile daha duyarlı hale geliyor (i5 dizüstü bilgisayarımda ve 60+ çekirdekli büyük Xeon sunucularında). CPU başına önbellek, işlemci başına bellek ayırma, işlemci zamanlayıcı ayırma ve işlem öncelikleri karmaşık yinelemelerle ilgili olduğunu düşünüyorum. Bence hiper-okumanın faydaları, nasıl kullanılacağını bilen cpu zamanlayıcıları yapmanın karmaşıklığı ile ağır basıyor.

Benim için, hiper-uç ile ilgili sorun şudur: Mantıksal çekirdeğe sahip olduğum kadar cpu-yoğun iş parçacığı başlatırsam, cpu yoğun görevler için hızlı bağlam anahtarlarına sahip olacağım; CPU yoğun görevler. Öte yandan, çok fazla cpu-yoğun iş parçacığı kadar fiziksel çekirdeğim varsa başlarsam, bu görevler için bağlam anahtarı ve arka plan görevleri için hızlı bağlam anahtarları olmaz. İyi görünüyor, ancak arka plan görevleri ücretsiz mantıksal işlemciler bulacak ve neredeyse engelsiz bir şekilde çalışacak. Gerçek zamanlı gösteri oldukları gibi (güzel -20).

İlk senaryoda, hiper iş parçacığı kullanışsızdır, arka plan görevleri pahalı bağlam anahtarları kullanacaktır çünkü normal işlemeyle hiper iş parçacığı maksimuma çıkardım. İkincisi kabul edilemez çünkü cpu gücümün% 50'sine kadar arkaplan işlerine öncelik veriliyor.

Bahsettiğim "işlemci yoğun" görevler yapay zeka veri madenciliği ve yetkilendirme sunucularıdır (işim). Ucuz bilgisayarlarda ve kümelerde blender oluşturma (gelecekteki evimi tasvir etmek için).

Ayrıca, bu tahmin işidir.

Daha iyi bir izlenim var, ama olmayabilir.


Benim senaryomun takip etmesi biraz daha kolay.
Paul M

9

Gerçekten eski çekirdekler için (Linux 2.6.9 ya da öylesine), noht parametresini önyükleme sırasında çekirdeğe ekleyin .

Bu çekirdek komut satırı seçeneği en az Linux 2.6.18'den beri kaldırılmıştır .


Gönderen http://www.faqs.org/docs/Linux-HOWTO/BootPrompt-HOWTO.html :

The `noht' Argument

This will disable hyper-threading on intel processors that have this feature. 

Lilo kullanıyorsanız /etc/lilo.conf (ve ardından lilo'yu çalıştırın) ya da grub kullanıyorsanız /boot/grub/menu.lst dosyasını düzenleyin.


Bu, işlevsel olarak BIOS'ta HT'yi devre dışı bırakmakla aynı mıdır?
ewwhite

Bundan emin değilim, ama evet, notanın BIOS'ta devre dışı bırakmaya eşdeğer olmasını beklerdim.
REMS

2
Bu bir Gentoo sistemidir. nohtGiriş grub grubunun komut satırında denedim . Sistem nohtkomutu yerine getirmedi . RHEL için aynı. Bakınız: bugzilla.redhat.com/show_bug.cgi?id=440321#c9
ewwhite

1
Bu en azından Linux 2.6.18’den beri kullanılmıyor . nohtÇekirdek seçeneği kaldırıldı. Bu talihsizdir, çünkü Linux yalnızca HT açık olduğunda bazı Haswell perf-counter hataları (BJ122, BV98, HSD29) için bir geçici çözüm sağlar , bu durum initramfs yüklenmeden önce gerçekleşir.
Peter Cordes

9

HT çiftindeki ikinci çekirdeği kapatmak için her çekirdek için "thread_siblings_list" öğesini kullanabilirsiniz.

Aşağıdaki komut satırı hack, optimize edilmemiş ve anlaşılmasını kolaylaştırmak için umarım bu şekilde yapılır.

cat /sys/devices/system/cpu/cpu*/topology/thread_siblings_list | \
awk -F, '{print $2}' | \
sort -n | \
uniq | \
( while read X ; do echo $X ; echo 0 > /sys/devices/system/cpu/cpu$X/online ; done )

bu nedenle, tüm iş parçacığı kardeş listelerini alın, her çift için ikinci CPU'yu çıkarın, benzersiz bir liste alın ve sonra bunları kapatın.

Bu mantıklı mı?

Yukarıdakileri çalıştırdıktan sonra "cat / proc / cpuinfo" yaparsam, çekirdek sayısı yarıya düşer.


Bu harika bir cevap. echo 0 > /sys/devices/system/cpu/cpu$X/onlineecho 0 | sudo tee /sys/devices/system/cpu/cpu$X/online
Amacım

5

Yeni Çekirdekler Eşzamanlı Çok Okuyuculu (SMT) kontrol sağlar.

SMT'nin durumunu;

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

İle durumu değiştir

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

Seçenekler;

  • üzerinde
  • kapalı
  • zorlamak

Bunu Linux Çekirdeği 4.4.0 ile test ettik.


Merhaba Nick ve siteye hoşgeldiniz. Testler (ve sürüm) hakkında bilgi oldukça değerlidir.
kubanczyk

Mükemmel, Ubuntu'da Test Edildi 16.04.6 LTS
Elder Geek

4

Lukas'ın cevabı güzel ancak HT'yi devre dışı bırakmak için gerçekten çalışmıyor çünkü çekirdek kimliği HT kardeşlerinin tanımlanmasına hizmet edemiyor. Bu komut dosyası yerine çalışır:

#!/bin/bash
for CPU in /sys/devices/system/cpu/cpu[0-9]*; do
    CPUID=`basename $CPU | cut -b4-`
    echo -en "CPU: $CPUID\t"
    [ -e $CPU/online ] && echo "1" > $CPU/online
    THREAD1=`cat $CPU/topology/thread_siblings_list | cut -f1 -d,`
    if [ $CPUID = $THREAD1 ]; then
        echo "-> enable"
        [ -e $CPU/online ] && echo "1" > $CPU/online
    else
        echo "-> disable"
        echo "0" > $CPU/online
    fi
done

Senaryonun bir varyasyonu. Emin olmak için birden fazla işlemciniz varsa ne olacağını kontrol etmeliyiz.
Paul M,

@PaulM İşte tam anlamıyla test ettiğim ve kullandığım amaçlar: 2 soketli Haswell sistemi.
Anton,

0

ILO / Drac’a girene kadar beklemek zorunda kaldım. Çekirdek önyükleme parametreleri geçerli Linux dağıtımlarında çalışmaz.


0

Libsmbios-bin paketinde (Debian, Ubuntu, etc), isCmosTokenActive ve activateCmosToken ikili dosyalarına sahipsiniz. Birlikte ile belirteç listede , daha sonra böyle bir şey deneyebilirsiniz:

# isCmosTokenActive 0x00d1 # CPU_Hyperthreading_Enable
[...] Type 0x00d1  Location 0x46 AND(fe) OR(0)  BITFIELD: 1
# isCmosTokenActive 0x00d2 # CPU_Hyperthreading_Disable
[....] Type 0x00d2  Location 0x46 AND(fe) OR(1)  BITFIELD: 0

Ardından CPU_Hyperthreading_Disable token'ı etkinleştirin:

# activateCmosToken 0x00d2 # CPU_Hyperthreading_Disable
[...] Type 0x00d2  Location 0x46 AND(fe) OR(1)  BITFIELD: 1

DOĞRULAYIN:

# isCmosTokenActive 0x00d1 # CPU_Hyperthreading_Enable
[...] Type 0x00d1  Location 0x46 AND(fe) OR(0)  BITFIELD: 0
# isCmosTokenActive 0x00d2 # CPU_Hyperthreading_Disable
[...] Type 0x00d2  Location 0x46 AND(fe) OR(1)  BITFIELD: 1

Şimdi, asıl soru, bunun etkili olması için yeniden başlatmaya ihtiyacınız olup olmadığı veya tam bir güç döngüsünün gerekli olup olmadığıdır. Deneyin ve nasıl geçtiğini görün!


0

Burada Paul M tarafından sağlanan bilgilere dayanarak, bu şekilde "script":

fgrep , /sys/devices/system/cpu/cpu*/topology/thread_siblings_list |
cut -d, -f2 | sort -u |
sudo xargs -rI, sh -c 'echo 0 > /sys/devices/system/cpu/cpu,/online'

Elbette , BIOS ile bağlantı kurmanın yapacağı şekilde hiper-iş parçacığını kapatmak değil , temelde sadece çekirdek görev zamanlayıcısına sahte çekirdek olduklarını bildiğimiz bazı çekirdeği kullanmamasını söyler.

Önceki durumuna /procveya /sysalt sistemin durumuna göre varsayımını yapan yazılım hala en düşük seviyede çalışıyor olabilir veya bu çalışma zamanı değişikliği nedeniyle başarısız olabilir, bu nedenle yeniden başlatılması gerekebilir. Örneğin, irqbalancebu koşullarda başarısızlığa eğilimli olduğunu fark ettim .


0

HT'yi devre dışı bırak:

echo 0 |sudo tee /sys/devices/system/cpu/cpu{4..7}/online

HT'yi etkinleştir:

echo 1 |sudo tee /sys/devices/system/cpu/cpu{4..7}/online

Not: Bu HyperThreading'i gerçekten devre dışı bırakmaz, ancak aynı sonucu elde eden "sahte" çekirdekleri devre dışı bırakır.


Kullanma şeklini seviyorum tee, ama bu hala soruya gerçek bir cevap sağlamada yetersiz kalıyor. Bu komutlar yalnızca belirli donanım yapılandırmaları için geçerlidir ve diğer donanım yapılandırmaları üzerinde istenmeyen etkilere neden olabilir. Ve bu komutların ne yaptıklarının bir açıklaması tamamen yoktur.
kasperd

0 kapalı ve 1 açık olduğundan, ilkinin 4 çekirdeği (bir sahtekarlıktaki sahtekarlıkta 8'in hiper-başlı açıkken) ve ikincisinin onları tekrar açtığını anlamanın kolay olduğunu düşünmüştüm. çekirdek bu sayı, {4..7} yerine {3,4} olmalıdır. Eğer octacore kullanıyorsanız, {8..15}
Zibri

0

Eski konu, ancak bu deneyi denemek için bir neden vardı. İlk olarak, çalışma zamanında (biraz sahte) CPU'ları devre dışı bırakmanın Hyperthreading'i önyüklemede devre dışı bırakmakla gerçekten eşdeğer olduğundan emin değilim. Bununla birlikte uygulamamızda küçük bir performans artışı olduğunu gördüm. (Ama saklamak için yeterli değil.)

Kullanılan thread_siblings bir etkinleştirme için anahtarın / devre dışı bırakma olarak değerini (hiper CPU'lar için ortak):

for i in /sys/devices/system/cpu/cpu[0-9]* 
do echo "$(cat $i/topology/thread_siblings) $i" 
done | 
awk '{v = (a[$1] ? 0 : 1); a[$1] = 1; print "echo " v " > " $2 "/online"}' | 
sudo sh 

Doğrulamayı doğrulamak için son sudo sh komutunu kullanarak w / o komutunu deneyin .

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.