我希望我的硬盘在闲置时停止旋转,比如说 20 分钟。任何分钟都可以,因为这个 NAS 很少使用。
我尝试过但没有效果的方法:
ataidle -S 20 /dev/ada0
只是立即降低驱动器的转速,计时器不起作用。一旦驱动器因访问而重新旋转,它们就会继续旋转。camcontrol standby /dev/ada0 -t 1200
与 的行为相同ataidle
。FreeNAS UI 的存储 -> 磁盘 -> 高级电源管理器设置只是调用
camcontrol
,同样,计时器不起作用。如果选择了允许待机的电源设置(例如 127),则驱动器几乎立即停止旋转(可能在 8 秒后),如果有任何访问,则会不断旋转和停止旋转。更新:请参阅 如何让 FreeNAS 降低磁盘转速? 了解有关如何完成这项工作的说明并跳过手动脚本。
我如何才能获得正常预期的“如果一段时间不使用则待机”行为?
FreeBSD 11.2-STABLE
通过使用FreeNAS 11.2
。驱动器是 4x Samsung 2TB 2.5" .T2000LM003`
# smartctl -P show /dev/ada0
smartctl 6.6 2017-11-05 r4594 [FreeBSD 11.2-STABLE amd64] (local build)
Copyright (C) 2002-17, Bruce Allen, Christian Franke, www.smartmontools.org
Drive found in smartmontools Database. Drive identity strings:
MODEL: ST2000LM003 HN-M201RAD
FIRMWARE: 2BC10007
match smartmontools Drive Database entry:
MODEL REGEXP: ST(1500|2000)LM0(03|04|06|07|10) HN-M[0-9]*RAD
FIRMWARE REGEXP: .*
MODEL FAMILY: Seagate Samsung SpinPoint M9T
ATTRIBUTE OPTIONS: None preset; no -v options are required.
答案1
谢谢你的想法。我已经为这个问题苦苦挣扎了几天。由于我不习惯编写 bash 脚本,所以我用 python3 重写了它。也许有人会觉得它有用:
import subprocess
import time
drives_to_check = ['ada3', 'ada4', 'ada5']
no_sleep_hours = ['00', '01']
seconds = 600
if time.strftime("%H") in no_sleep_hours:
exit()
o = subprocess.check_output(f'/usr/sbin/iostat -x -z -d {seconds} 2', shell=True)
for drive in drives_to_check:
if drive not in o.decode().split('extended')[-1]:
p = subprocess.check_output(f'/sbin/camcontrol cmd {drive} -a "E5 00 00 00 00 00 00 00 00 00 00 00" -r -', shell=True)
if p.decode()[27:29] != '00':
q = subprocess.check_output(f'/usr/local/sbin/ataidle -s /dev/{drive}', shell=True)
我的小插件是:当您不想运行脚本时,您可以将小时数添加到 no_sleep_hours。并且您必须将要检查的驱动器添加到“drives_to_check”,以便可以排除不应执行 spindown 的驱动器。也许您必须调整 iostat 和 ataidle 的路径,这些是 FreeNAS 中使用的路径。您可以使用以下方式找到您的路径:which adaidle
或which iostat
。您可以使用以下方式将其添加到 cron
*/15 * * * * /usr/local/bin/python3 /path/to/the/folder/check_disk_usage_and_spindown.py
答案2
更新:请参阅 https://serverfault.com/a/965694/184095 了解如何使 GUI 工作并跳过下面的手动脚本编写过程。
我最终手动完成了这项工作。编写一个脚本来检查驱动器活动,如果没有活动,则关闭驱动器,然后将此脚本安排为 cron 作业。
我决定采用一种方法来iostat
监控驱动器一段时间,在我的情况下是 600 秒(10 分钟)。如果iostat
报告没有使用,则调用ataidle -s /dev/ada[0123]
以暂停驱动器。我设置了一个 cron 作业,每 15 分钟调用一次此脚本:*/15 * * * * spindown_if_idle.sh 600
spindown_if_idle.sh
:
#!/bin/bash
# argument is the number of seconds to test for drive use, default to 5
if [ -z "$1" ]; then
SECONDS=5
else
SECONDS="$1"
fi
function list_ada_drives {
# emit a list of hard drives, i.e. ada0 ada1 ada2 ...
iostat -x | grep "ada" | awk '{print $1}'
}
function spindown {
# for every hard drive use ataidle to place it in standby
for ADA in $(list_ada_drives); do
ataidle -s /dev/$ADA
done
}
function are_drives_used {
# argument is number of seconds to test over
# run iostat for the specified number of seconds and ask to report any usage
# -z means to omit any drives that are idle
# iostat will print two reports, the first since boot and the second during the interval
# The first tail and grep strip off the first useless report. The second tail strips off the header
# The final grep strips off drives we're not interested in
iostat -x -z -d $SECONDS 2 | tail -n +2 | grep -A5000 "extended" | tail -n +3 | grep "ada" -q
}
if are_drives_used $SECONDS ; then
echo "Drives are being used"
else
echo "Drives are idle, going to standby"
spindown
fi
收集的指标
我尝试通过查询 记录的历史使用情况来避免这 10 分钟的阻塞collectd
。我曾经rrdtool fetch
查询 中存储的指标/var/db/collectd/rrd/localhost/disk-ada0
,但这些指标有几分钟的滞后。依赖它们意味着如果最近处于空闲状态,脚本可能会待机正在使用的驱动器。
测试驱动器是否旋转
以下脚本将报告每个驱动器是否处于空闲或旋转状态。对于测试很有用。
is_spinning.sh
:
#!/bin/sh
camcontrol devlist | grep ada | awk -F\( '{print $2'} | awk -F",|\\\\)" '{print $2}' |while read LINE
do
CM=$(camcontrol cmd $LINE -a "E5 00 00 00 00 00 00 00 00 00 00 00" -r - | awk '{print $10}')
if [ "$CM" = "FF" ] ; then
echo "$LINE: SPINNING"
elif [ "$CM" = "00" ] ; then
echo "$LINE: IDLE"
else
echo "$LINE: UNKNOWN"
fi
done
基于此论坛帖子。