Wie schalte ich Festplatten mit systemd aus?

Wie schalte ich Festplatten mit systemd aus?

Ich habe mehrere Ubuntu-Rechner mit sowohl einer SSD als auch einer herkömmlichen Festplatte, wobei die Festplatte nur gelegentlich verwendet wird.

Um Geräusche, Wärme und Stromverbrauch zu reduzieren und die Lebensdauer der Festplatte zu verlängern, möchte ich sie bei jedem Start ausschalten und nur bei Bedarf aktivieren.

hdparm -y(oder -Y) funktioniert auf der Befehlszeile ziemlich gut und macht genau das, was ich will.

Aber das Schreiben eines auszuführenden systemd-Dienstes hdparmfunktioniert nicht. Genauer gesagt: Es funktioniert, und die Platte geht tatsächlich in den Ruhezustand (wie das Debuggen zeigt), aber sie wird sofort wieder aufgeweckt (und bleibt wach), weil es etwas auf dem System gibt, das ganz am Ende des systemd-Bootvorgangs auf die Festplatten zugreift (und sie somit aufweckt).

Wie kann ich also einen hdparm -yBootvorgang so spät einfügen, dass ihm kein anderer Prozess mehr folgt?

Meine letzte Vermutung wäre, das Standardziel von systemd von grafisch auf ein neues (Sleepydisks) zu ändern, das dann vom früheren grafischen Ziel abhängt.

Aber gibt es nicht eine einfachere und unkompliziertere Möglichkeit, Festplatten auszuschalten?

Grüße

Antwort1

Öffnen Sie das Festplatten-Dienstprogramm und stellen Sie das Laufwerk so ein, dass es nach 10 Minuten Inaktivität automatisch herunterfährt.

Antwort2

Verwenden Sie die Option -S von hdparm. Dadurch wird das Spindown-Timeout festgelegt, das vom Laufwerk eingehalten werden soll.

$ hdparm --help
-S   Set standby (spindown) timeout

$ hdparm -S 60 /dev/sdd
/dev/sdd:
 setting standby to 60 (5 minutes)

Beachten Sie, dass dies ein großes „S“ ist.

Antwort3

Ich verwende das folgende Skript, um im Leerlauf befindliche Festplatten zum Herunterfahren zu „zwingen“, wobei ich mit „zwingen“ eine direkte Anweisung an das Laufwerk meine, da viele WD-Laufwerke beim Herunterfahren problematisch sind. Vielleicht können Sie dies Ihren Anforderungen cronentsprechend erweitern. Das Skript ist gut kommentiert, sodass Sie es ganz einfach ändern können sollten. Ich rufe es alle 20 Minuten auf und passe es bei Bedarf an:

spindown.sh

#!/usr/bin/env bash

logger "[SPINDOWN] Checking disk activity and spinning down idles..."

# Exit during maintenance
if pgrep snapraid > /dev/null; then
    logger "[SPINDOWN] Detected snapRAID maintenance. Exiting.";
    exit 0
fi

# Specify any drives you want to ignore; separate multiple drives by spaces; e.g. "sda sdb"
IGNORE_DRIVES=""

PATH='/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin'

# Check for idle disks and spin them down unless smartd is running tests

# Create a file on the ramdisk and cycle it to test for disk activity
(   if [ ! -f /dev/shm/diskstats_1 ]; then 
        logger "[SPINDOWN] Creating initial state file on ramdisk";
        touch /dev/shm/diskstats_1;
    fi ; 
    logger "[SPINDOWN] Updating state files on ramdisk";
    mv /dev/shm/diskstats_1 /dev/shm/diskstats_2; 
    cat /proc/diskstats > /dev/shm/diskstats_1 ) > /dev/null 2>&1

# Find all removable USB drives, so we can ignore them later,
# see http://superuser.com/a/465953
REMOVABLE_DRIVES=""
for _device in /sys/block/*/device; do
    if echo $(readlink -f "$_device")|egrep -q "usb"; then
        _disk=$(echo "$_device" | cut -f4 -d/)
        REMOVABLE_DRIVES="$REMOVABLE_DRIVES $_disk"
    fi
done

# Append detected removable drives to manually ignored drives
IGNORE_DRIVES="$IGNORE_DRIVES $REMOVABLE_DRIVES"

# Loop through all the array disks and spin down the idle disks. Will find all drives sda > sdz AND sdaa > sdaz...
logger "[SPINDOWN] Looping through drives to detect idle state"
for disk in `find /dev/ -regex '/dev/sd[a-z]+' | cut -d/ -f3`
do
    # Skip removable USB drives and those the user wants to ignore
    if [[ $IGNORE_DRIVES =~ $disk ]]; then
        continue
    fi

    # Skip SSDs
    if [[ $(cat /sys/block/$disk/queue/rotational) -eq 0 ]]; then
        continue
    fi

    # Check if drive exists
    if [ -e /dev/$disk ]; then
        logger "[SPINDOWN] Checking drive $disk"
        # Check if drive is currently spinning
        if [ "$(smartctl -i -n standby /dev/$disk | grep "ACTIVE or IDLE")" ]; then
            logger "[SPINDOWN] Disk $disk is ACTIVE or IDLE. Checking for selftest"
            # Check if smartctl is currently not running a self test
            if [ $(smartctl -a /dev/$disk | grep -c "Self-test routine in progress") = 0 ]; then
            logger "[SPINDOWN] Disk $disk is not running a self test. Checking activity."
                # Check if drive has been non idle since last run
                if [ "$(diff /dev/shm/diskstats_1 /dev/shm/diskstats_2 | grep $disk )" = "" ]; then
                    logger "[SPINDOWN] Spinning down /dev/$disk `df -h | grep /dev/$disk | rev | cut -d ' ' -f 1 | rev`"
                    hdparm -y /dev/$disk
                fi
            else
                logger "[SPINDOWN] /dev/$disk is running Self-test routine. Skipping."
            fi
        fi
    fi
done

Gemäß der spezifischen Frage, wie geht das mit systemd? ... erstellen Sie eine Timer-Datei, die dieses Skript aufruft (Ref:https://wiki.archlinux.org/index.php/Systemd/Timers)

verwandte Informationen