Skip to content

Commit

Permalink
Merge pull request #2970 from freenas/NAS-100168
Browse files Browse the repository at this point in the history
NAS-100168 / 11.3 / disk.sata_dom_lifetime_left
  • Loading branch information
themylogin committed May 2, 2019
2 parents 79275c9 + c6bad3f commit 38c6c53
Show file tree
Hide file tree
Showing 2 changed files with 50 additions and 0 deletions.
13 changes: 13 additions & 0 deletions src/middlewared/middlewared/plugins/disk.py
Expand Up @@ -38,6 +38,7 @@
RE_IDENTIFIER = re.compile(r'^\{(?P<type>.+?)\}(?P<value>.+)$')
RE_ISDISK = re.compile(r'^(da|ada|vtbd|mfid|nvd|pmem)[0-9]+$')
RE_MPATH_NAME = re.compile(r'[a-z]+(\d+)')
RE_SATA_DOM_LIFETIME = re.compile(r'^164\s+.*\s+([0-9]+)$', re.M)
RE_SED_RDLOCK_EN = re.compile(r'(RLKEna = Y|ReadLockEnabled:\s*1)', re.M)
RE_SED_WRLOCK_EN = re.compile(r'(WLKEna = Y|WriteLockEnabled:\s*1)', re.M)
RAWTYPE = {
Expand Down Expand Up @@ -1729,6 +1730,18 @@ async def camcontrol_idle():

asyncio.ensure_future(camcontrol_idle())

@private
async def sata_dom_lifetime_left(self, devname):
try:
smartctl = (await run('smartctl', '-A', devname, encoding="utf8", errors="ignore")).stdout
except subprocess.CalledProcessError:
return None

m = RE_SATA_DOM_LIFETIME.search(smartctl)
if m:
aec = int(m.group(1))
return max(1.0 - aec / 3000, 0)


def new_swap_name():
"""
Expand Down
37 changes: 37 additions & 0 deletions src/middlewared/middlewared/pytest/unit/plugins/test_disk.py
@@ -0,0 +1,37 @@
import textwrap
from unittest.mock import patch

from asynctest import CoroutineMock, Mock
import pytest

from middlewared.plugins.disk import DiskService
from middlewared.pytest.unit.middleware import Middleware


@pytest.mark.asyncio
async def test__disk_service__sata_dom_lifetime_left():

m = Middleware()

with patch("middlewared.plugins.disk.run", CoroutineMock(return_value=Mock(stdout=textwrap.dedent("""\
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
=== START OF READ SMART DATA SECTION ===
SMART Attributes Data Structure revision number: 0
Vendor Specific SMART Attributes with Thresholds:
ID# ATTRIBUTE_NAME FLAG VALUE WORST THRESH TYPE UPDATED WHEN_FAILED RAW_VALUE
9 Power_On_Hours 0x0012 100 100 000 Old_age Always - 8693
12 Power_Cycle_Count 0x0012 100 100 000 Old_age Always - 240
163 Unknown_Attribute 0x0000 100 100 001 Old_age Offline - 1065
164 Unknown_Attribute 0x0000 100 100 001 Old_age Offline - 322
166 Unknown_Attribute 0x0000 100 100 010 Old_age Offline - 0
167 Unknown_Attribute 0x0022 100 100 000 Old_age Always - 0
168 Unknown_Attribute 0x0012 100 100 000 Old_age Always - 0
175 Program_Fail_Count_Chip 0x0013 100 100 010 Pre-fail Always - 0
192 Power-Off_Retract_Count 0x0012 100 100 000 Old_age Always - 208
194 Temperature_Celsius 0x0022 060 060 030 Old_age Always - 40 (Min/Max 30/60)
241 Total_LBAs_Written 0x0032 100 100 000 Old_age Always - 14088053817
""")))):
assert abs(await DiskService(m).sata_dom_lifetime_left("ada1") - 0.8926) < 1e-4

0 comments on commit 38c6c53

Please sign in to comment.