日志磁盘旋转和旋转

日志磁盘旋转和旋转

我有一个在 Ubuntu 18.04 上运行的文件/媒体服务器。它有 1 个 SSD,上面安装了 Ubuntu,还有 4 个 HDD,用于存储各种文件。我找到了一些关于如何记录磁盘活动的信息,这些信息似乎很简单(比如 iotop)。但是,我也想记录以下内容,但找不到如何执行此操作:

  • 磁盘旋转的准确时间
  • 什么过程/活动负责磁盘旋转
  • 磁盘再次旋转停止的确切时间

有人知道一种(简单的)方法来做到这一点吗?

答案1

对于记录旋转加速和旋转减速,hd-idle 应该足够了:https://github.com/adelolmo/hd-idlehd-idle 只会记录其自身触发的启动/停止。我编写了一个脚本来监控这一点:

import subprocess
import time
import re
from pathlib import Path
import logging

logging.basicConfig(level=logging.INFO, format='%(asctime)s %(filename)s %(levelname)s %(message)s',)
logger = logging.getLogger('hd-spin-log')

DISK_BLACKLIST = ['sda']

def get_all_disk_status():
    ret = {}
    for path in Path('/dev').glob('sd*'):
        if path.name[-1].isdigit():
            continue
        if path.name in DISK_BLACKLIST:
            continue
        try:
            statOut = subprocess.check_output(['hdparm', '-C', str(path)]).decode()
        except Exception:
            ret[path.name] = '(hdparm fail)'
            logger.warning('hdparm failed!', exc_info=True)
            return
        m = re.findall(r'(?m)drive state is:  (.*?)$', statOut)
        if m:
            ret[path.name] = m[0]
        else:
            ret[path.name] = '(unknown)'
            logger.warning("Failed to parse drive state for %s, output %s", path, statOut)
    return ret

def main():
    logger.info("monitor start")
    lastStat = get_all_disk_status()
    logger.debug("first time stat: %s", lastStat)
    while True:
        try:
            curStat = get_all_disk_status()
            logger.debug('cur stat: %s', curStat)
            if curStat != lastStat:
                # stat changed!
                disks = set(list(curStat.keys()) + list(lastStat.keys()))
                for d in disks:
                    if d in lastStat and d in curStat:
                        if lastStat[d] != curStat[d]:
                            logger.info('disk %s: %s -> %s', d, lastStat[d], curStat[d])
                    elif d in lastStat and d not in curStat:
                        logger.info('disk %s: %s -> [disappeared]', d, lastStat[d])
                    elif d not in lastStat and d in curStat:
                        logger.info('disk %s: [new] -> %s', d, curStat[d])
                    else:
                        assert False
            else:
                logger.debug('disk stat not changed...')
            lastStat = curStat
        except Exception:
            logger.warning("exception during check!", exc_info=True)
        time.sleep(10)

main()

示例日志:

2023-05-17 23:09:39,866 hd-spin-log.py INFO monitor start
2023-05-17 23:09:59,916 hd-spin-log.py INFO disk sdc: unknown -> standby

对于旋转罪魁祸首,fatrace 可能是一个不错的选择。

相关内容