Linux’ta MSI Tabanlı Laptop Fan Kontrolü: “Firmware Desteklenmiyor” Hatasını Çözmek


Linux’ta MSI Tabanlı Laptop Fan Kontrolü: “Firmware Desteklenmiyor” Hatasını Çözmek

GameGaraj Slayer 4 (i7-14700HX + RTX 4060) laptopumda CachyOS kurduktan sonra karşılaştığım ikinci donanım sorunu fan/sıcaklık kontrolüydü. sensors komutu CPU ve NVMe sıcaklıklarını sorunsuz gösteriyordu, ama fan RPM değeri hiçbir yerde yoktu. Sebebi basit: bu tarz laptoplarda fan verisi standart lm_sensors sürücüleri üzerinden değil, laptopun EC (Embedded Controller) üzerinden okunuyor — ve EC, üreticiye özel, dokümante edilmemiş bir protokol kullanıyor.

Bu yazı, aynı duruma düşüp “modülüm cihazımı tanımıyor” hatasıyla karşılaşan MSI/Clevo tabanlı laptop sahipleri için attığım tüm adımları ve kalıcı çözümü anlatıyor.

Not: Bu yöntem, klavye RGB yazımda anlattığım PID uyarlamasına çok benziyor — yine “açık kaynak araç, benim modelimi resmi olarak desteklemiyor ama alt yapı zaten orada” durumu. Farkı, burada tek bir sayı değil, kernel modülünün içine gömülü bir firmware kimlik listesi değiştiriliyor.

1. Doğru Aracı Bulmak

İlk aklıma gelen nbfc-linux oldu, ama ne GameGaraj Slayer 4 için ne de yakın MSI/Clevo modelleri için hazır bir profil vardı. Onun yerine MSI laptoplara özel yazılmış gerçek bir kernel modülü olan msi-ec‘i kullandım. Bu modül, hwmon ve platform katmanları üzerinden EC’ye doğrudan erişiyor ve fan modu, CPU/GPU shift modu, Cooler Boost gibi kontrolleri sisteme /sys/devices/platform/msi-ec/ altında açıyor.

CachyOS’ta (Arch tabanlı herhangi bir dağıtımda) kurulumu AUR üzerinden:

paru -S msi-ec-dkms-git

2. “Operation not supported” Hatası

Kurulumdan sonra modülü yüklemeye çalıştığımda:

sudo modprobe msi-ec

karşıma Operation not supported hatası çıktı. Sebebi: msi-ec, her laptop modelini değil, yalnızca tanıdığı EC firmware versiyonlarının bir listesini destekliyor. Benim laptopumun firmware’i bu listede yoktu.

3. Doğru Firmware Kimliğini Bulmak

Buradaki en kritik hata payı, BIOS versiyonu ile EC firmware versiyonunu karıştırmak. İlk denediğim:

dmidecode -s bios-version

E15P2IE2.108 verdi. Bu BIOS versiyonuydu, msi-ec‘in aradığı EC firmware’i değil — yanlış iz.

Gerçek EC firmware string’ini öğrenmek için modülü debug modunda yükleyip debug dosyasından okumak gerekiyor:

sudo modprobe msi-ec debug=1
cat /sys/devices/platform/msi-ec/debug/fw_version

Bu bana gerçek EC firmware’imi verdi: 15P2ED61.100

4. Kaynak Koduna Firmware’i Elle Eklemek

msi-ec‘in DKMS kaynağında (/usr/src/msi-ec-<versiyon>/msi-ec.c), desteklenen modeller firmware string’lerine göre eşleniyor. En yakın desteklenen model, MSI Sword 16 HX’in (15P2EMS1.xxx) bulunduğu listeydi — GameGaraj Slayer 4’ün de aynı donanım ailesinin bir türevi (rebrand) olduğunu gösteriyor. Firmware’imi bu listeye elle ekledim:

sudo sed -i '/"15P2EMS1.110",/a\        "15P2ED61.100", // GameGaraj Slayer 4 (MSI Sword 16 HX derivative)' /usr/src/msi-ec-<versiyon>/msi-ec.c

<versiyon> kısmını kendi /usr/src/ altındaki msi-ec-* klasör adına göre değiştirin (ls /usr/src/ | grep msi-ec ile görebilirsiniz).

5. Modülü Yeniden Derlemek

Kaynağı değiştirdikten sonra DKMS ile modülü kaldırıp yeniden derledim:

sudo dkms remove msi-ec/<versiyon> -k $(uname -r)
sudo dkms build msi-ec/<versiyon> -k $(uname -r)
sudo dkms install msi-ec/<versiyon> -k $(uname -r)
sudo modprobe msi-ec

Bu adımdan sonra /sys/devices/platform/msi-ec/ altında cpu/, gpu/, fan_mode, shift_mode gibi tam kontrol dosyaları belirdi — donanım artık tanınıyordu.

6. Grafik Arayüz: MControlCenter

Sysfs dosyalarıyla elle uğraşmak istemeyenler için msi-ec‘in üzerine kurulu bir GUI var:

paru -S mcontrolcenter-bin

Bu araçla sıcaklık, fan RPM ve performans modları (Silent/Balanced/Extreme/Cooler Boost gibi) grafik arayüzde görünür ve değiştirilebilir hale geldi.

7. Kalıcı Hale Getirmek

Değişikliklerin her açılışta geçerli olması için iki ayar gerekiyor:

a) Modülün otomatik yüklenmesi/etc/modules-load.d/msi-ec.conf dosyasına tek satır:

msi-ec

b) MControlCenter’ın otomatik başlaması — uygulamanın .desktop dosyasını autostart klasörüne kopyalamak:

cp /usr/share/applications/mcontrolcenter.desktop ~/.config/autostart/

8. Asıl Sorun: Güncellemeler Kaynak Değişikliğini Siliyor

msi-ec-dkms-git bir -git paketi; yani paru -Syu her çalıştığında yukarı akıştaki (upstream) en son kaynak yeniden indiriliyor ve 5. adımda elle eklediğim firmware satırı siliniyor. Yani her güncelleme sonrası /sys/devices/platform/msi-ec/ klasörü kayboluyor ve fan kontrolü bozuluyor.

Bunu elle her seferinde düzeltmek yerine, süreci tamamen otomatikleştirdim:

a) Otomatik düzeltme betiği/usr/local/bin/fix-msi-ec-firmware.sh, firmware satırını (15P2ED61.100) kaynağa tekrar ekleyip modülü otomatik olarak yeniden derliyor.

b) Pacman hook/etc/pacman.d/hooks/msi-ec-firmware-fix.hook, msi-ec-dkms-git paketi her güncellendiğinde bu betiği otomatik tetikliyor. Böylece manuel müdahaleye gerek kalmıyor; güncelleme bittiği anda firmware satırı geri ekleniyor ve modül yeniden derleniyor.

Elle Müdahale Gerekirse

Hook bir şekilde tetiklenmezse veya elle kontrol etmek isterseniz, tek yapmanız gereken:

sudo /usr/local/bin/fix-msi-ec-firmware.sh
sudo rmmod msi_ec
sudo modprobe msi-ec

Tek Komutla Otomatik Kurulum Betiği

Yukarıdaki 1-8 arası adımları her yeni kurulumda (veya “-git” paketinin güncellemede kaynağı sıfırlaması durumunda) elle tekrarlamak yerine, tüm süreci tek bir betikte topladım. Betik şunları otomatik yapıyor:

  • msi-ec-dkms-git ve mcontrolcenter-bin paketlerini kurar
  • Modülü debug=1 ile yükleyip gerçek EC firmware’inizi otomatik okur (BIOS versiyonuyla karıştırmadan)
  • Normal modprobe msi-ec deneyip firmware’inizin zaten destekleniyor olup olmadığını kontrol eder
  • Desteklenmiyorsa, kaynak koddaki en yakın aynı aile (prefix) firmware kaydını bulup kendi firmware’inizi otomatik olarak o listeye ekler
  • DKMS ile modülü yeniden derler ve yükler
  • Modülün her açılışta otomatik yüklenmesini (modules-load.d) ve MControlCenter’ın otomatik başlamasını (autostart) ayarlar
  • Kalıcılık için bir düzeltme betiği (fix-msi-ec-firmware.sh) ve bir pacman hook‘u kurar, böylece msi-ec-dkms-git her güncellendiğinde firmware kaydı otomatik olarak geri eklenir

Betiği msi_ec_fan_kurulum.sh adıyla kaydedin:

#!/bin/bash
set -e

echo "=== MSI-EC Fan/Sıcaklık Kontrolü Otomatik Kurulum Aracı ==="

if [ "$EUID" -ne 0 ]; then
    echo "Lütfen betiği sudo ile çalıştırın: sudo ./msi_ec_fan_kurulum.sh"
    exit 1
fi

REAL_USER="${SUDO_USER:-$USER}"
REAL_HOME=$(getent passwd "$REAL_USER" | cut -d: -f6)

# 1. Bağımlılıklar ve paketler
echo "[1/8] Gerekli paketler kuruluyor..."
if command -v pacman &> /dev/null; then
    if ! command -v paru &> /dev/null; then
        echo "Hata: 'paru' bulunamadı. AUR paketleri için bir AUR yardımcısı gerekli."
        exit 1
    fi
    sudo -u "$REAL_USER" paru -S --needed --noconfirm msi-ec-dkms-git mcontrolcenter-bin dmidecode
else
    echo "Hata: Bu betik şu an sadece Arch tabanlı (pacman) dağıtımlar için hazırlandı."
    exit 1
fi

DKMS_DIR=$(find /usr/src -maxdepth 1 -type d -name "msi-ec-*" | sort -V | tail -n1)
if [ -z "$DKMS_DIR" ]; then
    echo "Hata: /usr/src altında msi-ec kaynak klasörü bulunamadı."
    exit 1
fi
DKMS_VERSION=$(basename "$DKMS_DIR" | sed 's/msi-ec-//')
SRC_FILE="$DKMS_DIR/msi-ec.c"
echo "Bulunan msi-ec sürümü: $DKMS_VERSION"

# 2. Gerçek EC firmware'ini debug modunda oku
echo "[2/8] EC firmware kimliği tespit ediliyor (debug modu)..."
rmmod msi_ec 2>/dev/null || true
modprobe msi-ec debug=1 2>/dev/null || true
sleep 1

FW_FILE="/sys/devices/platform/msi-ec/debug/fw_version"
if [ ! -f "$FW_FILE" ]; then
    echo "Hata: Firmware bilgisi okunamadı ($FW_FILE bulunamadı)."
    echo "Laptopunuzun EC'si bu yöntemle desteklenmiyor olabilir."
    rmmod msi_ec 2>/dev/null || true
    exit 1
fi

FW_ID=$(cat "$FW_FILE" | tr -d '[:space:]')
echo "Tespit edilen EC firmware: $FW_ID"
rmmod msi_ec 2>/dev/null || true

# 3. Firmware zaten destekleniyor mu kontrol et
echo "[3/8] Firmware'in zaten desteklenip desteklenmediği kontrol ediliyor..."
if modprobe msi-ec 2>/dev/null; then
    echo "Firmware ($FW_ID) zaten destekleniyor, kaynak yaması gerekmiyor."
    ALREADY_SUPPORTED=1
    rmmod msi_ec 2>/dev/null || true
else
    ALREADY_SUPPORTED=0
fi

# 4. Desteklenmiyorsa kaynağa ekle
if [ "$ALREADY_SUPPORTED" -eq 0 ]; then
    echo "[4/8] Firmware desteklenmiyor, kaynak yamalanıyor..."

    if grep -q "\"$FW_ID\"" "$SRC_FILE"; then
        echo "Firmware zaten kaynakta mevcut, tekrar eklenmiyor."
    else
        # Aynı aile (ilk 4 karakter) içindeki en yakın satırı bul ve hemen altına ekle
        PREFIX="${FW_ID:0:4}"
        ANCHOR_LINE=$(grep -n "\"$PREFIX" "$SRC_FILE" | tail -n1 | cut -d: -f1)

        if [ -z "$ANCHOR_LINE" ]; then
            echo "Uyarı: '$PREFIX' ile başlayan bir referans satır bulunamadı."
            echo "Lütfen $SRC_FILE dosyasını elle inceleyip firmware'i (\"$FW_ID\") uygun listeye ekleyin."
            exit 1
        fi

        sed -i "${ANCHOR_LINE}a\\        \"$FW_ID\", // Auto-added by msi_ec_fan_kurulum.sh ($(date +%F))" "$SRC_FILE"
        echo "Firmware '$FW_ID', $ANCHOR_LINE. satırın altına eklendi."
    fi

    # 5. Modülü yeniden derle
    echo "[5/8] Modül yeniden derleniyor (DKMS)..."
    dkms remove "msi-ec/$DKMS_VERSION" -k "$(uname -r)" 2>/dev/null || true
    dkms build "msi-ec/$DKMS_VERSION" -k "$(uname -r)"
    dkms install "msi-ec/$DKMS_VERSION" -k "$(uname -r)"
fi

# 6. Modülü yükle ve doğrula
echo "[6/8] Modül yükleniyor..."
modprobe msi-ec
if [ -d /sys/devices/platform/msi-ec ]; then
    echo "Başarılı: /sys/devices/platform/msi-ec/ oluştu, donanım tanındı."
else
    echo "Uyarı: Modül yüklendi ama /sys/devices/platform/msi-ec/ bulunamadı. Elle kontrol edin."
fi

# 7. Kalıcılık: otomatik yükleme, autostart, düzeltme betiği ve pacman hook'u
echo "[7/8] Kalıcılık ayarları yapılıyor..."

echo "msi-ec" > /etc/modules-load.d/msi-ec.conf

mkdir -p "$REAL_HOME/.config/autostart"
if [ -f /usr/share/applications/mcontrolcenter.desktop ]; then
    cp /usr/share/applications/mcontrolcenter.desktop "$REAL_HOME/.config/autostart/"
    chown "$REAL_USER":"$REAL_USER" "$REAL_HOME/.config/autostart/mcontrolcenter.desktop"
fi

cat > /usr/local/bin/fix-msi-ec-firmware.sh << EOF
#!/bin/bash
# msi_ec_fan_kurulum.sh tarafından otomatik oluşturuldu.
# msi-ec-dkms-git güncellemesi sonrası firmware kaydını geri ekler ve modülü yeniden derler.
set -e
FW_ID="$FW_ID"
DKMS_DIR=\$(find /usr/src -maxdepth 1 -type d -name "msi-ec-*" | sort -V | tail -n1)
DKMS_VERSION=\$(basename "\$DKMS_DIR" | sed 's/msi-ec-//')
SRC_FILE="\$DKMS_DIR/msi-ec.c"

if ! grep -q "\"\$FW_ID\"" "\$SRC_FILE"; then
    PREFIX="\${FW_ID:0:4}"
    ANCHOR_LINE=\$(grep -n "\"\$PREFIX" "\$SRC_FILE" | tail -n1 | cut -d: -f1)
    if [ -n "\$ANCHOR_LINE" ]; then
        sed -i "\${ANCHOR_LINE}a\\\\        \"\$FW_ID\", // Re-added by fix-msi-ec-firmware.sh" "\$SRC_FILE"
    fi
fi

dkms remove "msi-ec/\$DKMS_VERSION" -k "\$(uname -r)" 2>/dev/null || true
dkms build "msi-ec/\$DKMS_VERSION" -k "\$(uname -r)"
dkms install "msi-ec/\$DKMS_VERSION" -k "\$(uname -r)"
rmmod msi_ec 2>/dev/null || true
modprobe msi-ec
echo "msi-ec firmware düzeltmesi tamamlandı (\$FW_ID)."
EOF
chmod +x /usr/local/bin/fix-msi-ec-firmware.sh

mkdir -p /etc/pacman.d/hooks
cat > /etc/pacman.d/hooks/msi-ec-firmware-fix.hook << 'EOF'
[Trigger]
Operation = Install
Operation = Upgrade
Type = Package
Target = msi-ec-dkms-git

[Action]
Description = msi-ec firmware kaydı geri ekleniyor ve modül yeniden derleniyor...
When = PostTransaction
Exec = /usr/local/bin/fix-msi-ec-firmware.sh
EOF

echo "[8/8] Tamamlandı."
echo ""
echo "=== Kurulum Tamamlandı! ==="
echo "Firmware: $FW_ID"
echo "Fan/sıcaklık kontrolleri: /sys/devices/platform/msi-ec/"
echo "Grafik arayüz: MControlCenter (uygulama menüsünde veya 'mcontrolcenter' komutuyla)"
echo "Not: msi-ec-dkms-git her güncellendiğinde firmware kaydı otomatik olarak korunacak."

Çalıştırma izni verin ve başlatın:

chmod +x msi_ec_fan_kurulum.sh
sudo ./msi_ec_fan_kurulum.sh

Betik zaten desteklenen bir firmware’de çalıştırılırsa (yani sizin modeliniz msi-ec listesinde varsa) kaynak yaması adımını otomatik olarak atlıyor ve sadece kalıcılık ayarlarını yapıyor — yani hem “hiç desteklenmeyen” hem de “zaten destekleniyor ama kalıcı hale getirilmemiş” durumlarında güvenle çalıştırılabilir.

Uyarı: Betik, firmware’inizi kaynağa eklerken sizinkiyle aynı 4 karakterlik önekte (15P2 gibi) başlayan en yakın satırı otomatik buluyor. Bu, aynı üretici/EC ailesindeki laptoplar için genelde işe yarıyor, ama garantili değil — betik çalıştıktan sonra mutlaka /sys/devices/platform/msi-ec/ altında beklediğiniz dosyaların (fan_mode, cpu/, gpu/ vb.) oluştuğunu kontrol edin. Anchor satırı bulunamazsa betik sizi bilgilendirip duruyor, kör bir şekilde ilerlemiyor.

Genelleştirme: Kendi Modeliniz İçin Bu Yöntemi Nasıl Uygularsınız?

Bu yazı GameGaraj Slayer 4’e özel gibi görünse de, aslında aynı donanım ailesindeki (rebrand) her MSI laptop için genelleştirilebilir bir tarif:

  1. sensors çıktısında fan RPM yoksa, muhtemelen EC üzerinden okunuyor demektir.
  2. msi-ec kurun, modprobe msi-ec deneyin. Operation not supported alırsanız firmware’iniz listede değildir.
  3. dmidecode -s bios-version ile karıştırmayındebug=1 parametresiyle yükleyip /sys/devices/platform/msi-ec/debug/fw_version dosyasından gerçek EC firmware’inizi okuyun.
  4. msi-ec.c kaynağındaki model listesine bakıp firmware öneki (15P2E... gibi) size en yakın olan modeli bulun — genelde aynı anakart/EC tasarımını paylaşan bir “kardeş model”dir.
  5. Firmware’inizi o modelin yanına ekleyip DKMS ile yeniden derleyin.
  6. -git paketi kullanıyorsanız, güncelleme sonrası değişikliğin silineceğini unutmayın — bir pacman hook’u (veya apt/dnf kullanıyorsanız benzer bir post-install script) ile otomatikleştirin.

Özet

Fan kontrolü bu tarz laptoplarda genelde “desteklenmiyor” değil, sadece henüz listeye eklenmemiş oluyor. msi-ec gibi projeler protokolü zaten çözmüş durumda; eksik olan çoğu zaman sizin firmware string’inizin tanınan modeller listesinde yer almaması. Doğru firmware kimliğini bulup kaynağa ekledikten sonra iş, bunu güncellemelere dayanıklı hale getirmekte.

Aynı duruma düşerseniz veya farklı bir MSI/Clevo modelinde denerseniz, jn7.net üzerinden bana ulaşabilirsiniz.


Kaynak proje: msi-ec — bu yazı projenin kendisiyle değil, resmi olarak desteklenmeyen bir firmware’e nasıl uyarlandığıyla ilgilidir.

cachyosdkmsfan controlhardwarekdelinuxmsi-ec
Comments (0)
Add Comment