Blob Blame History Raw
From 7ecf84e7958cd901b5190073afb6204f1d9c73e7 Mon Sep 17 00:00:00 2001
From: Gris Ge <fge@redhat.com>
Date: Fri, 8 Dec 2017 19:03:42 +0800
Subject: [PATCH 1/3] MegaRAID plugin: Fix cache information query.

 * MegaRAID always enable read cache. Old code treat that as read ahead
   cache which is not what we defined in API document.

 * Fix the write cache set function to handle 'Cache I/O'.

 * Inform user via volume_read_cache_policy_update(): read cache is
   always enabled, if they are looking for read ahead cache setting, they
   should use storcli/perccli.

Signed-off-by: Gris Ge <fge@redhat.com>
---
 plugin/megaraid/megaraid.py | 77 ++++++++++++++++++++++++++++-----------------
 1 file changed, 48 insertions(+), 29 deletions(-)

diff --git a/plugin/megaraid/megaraid.py b/plugin/megaraid/megaraid.py
index 8982ff9a..25b900da 100644
--- a/plugin/megaraid/megaraid.py
+++ b/plugin/megaraid/megaraid.py
@@ -1067,9 +1067,6 @@ def volume_cache_info(self, volume, flags=Client.FLAG_RSVD):
         sys_all_output = self._storcli_exec(
             ["/%s" % vd_path.split('/')[1], "show", "all"])
 
-        write_cache_status = Volume.WRITE_CACHE_STATUS_WRITE_THROUGH
-        read_cache_status = Volume.READ_CACHE_STATUS_DISABLED
-
         ram_size = _mega_size_to_lsm(
             sys_all_output['HwCfg'].get('On Board Memory Size', '0 KB'))
         if ram_size > 0:
@@ -1081,36 +1078,42 @@ def volume_cache_info(self, volume, flags=Client.FLAG_RSVD):
                 flag_battery_ok = True
 
         lsi_cache_setting = vd_basic_info['Cache']
-        if lsi_cache_setting[0] == 'R':
-            read_cache_policy = Volume.READ_CACHE_POLICY_ENABLED
-            if flag_has_ram:
-                read_cache_status = Volume.READ_CACHE_STATUS_ENABLED
-        elif lsi_cache_setting[0:2] == 'NR':
-            read_cache_policy = Volume.READ_CACHE_POLICY_DISABLED
-        else:
-            raise LsmError(
-                ErrorNumber.PLUGIN_BUG,
-                "Unknown read cache %s for volume %s" %
-                (lsi_cache_setting, vd_path))
+        # According to MegaRAID document, read I/O is always cached for direct
+        # I/O and cache I/O.
+        read_cache_policy = Volume.READ_CACHE_POLICY_ENABLED
+        write_cache_status = Volume.WRITE_CACHE_STATUS_WRITE_THROUGH
+        read_cache_status = Volume.READ_CACHE_STATUS_DISABLED
 
-        if 'AWB' in lsi_cache_setting:
+        if lsi_cache_setting.endswith('D'):
+            # Direct I/O
+            if 'AWB' in lsi_cache_setting:
+                write_cache_policy = Volume.WRITE_CACHE_POLICY_WRITE_BACK
+            elif 'WB' in lsi_cache_setting:
+                write_cache_policy = Volume.WRITE_CACHE_POLICY_AUTO
+            elif 'WT' in lsi_cache_setting:
+                write_cache_policy = Volume.WRITE_CACHE_POLICY_WRITE_THROUGH
+            else:
+                raise LsmError(
+                    ErrorNumber.PLUGIN_BUG,
+                    "Unknown write cache %s for volume %s" %
+                    (lsi_cache_setting, vd_path))
+        elif lsi_cache_setting.endswith('C'):
+            # cache I/O always caches write and read and ignore changes.
             write_cache_policy = Volume.WRITE_CACHE_POLICY_WRITE_BACK
-            if flag_has_ram:
-                write_cache_status = Volume.WRITE_CACHE_STATUS_WRITE_BACK
-        elif 'WB' in lsi_cache_setting:
-            # This mode means enable write cache when battery or CacheVault
-            # is healthy.
-            write_cache_policy = Volume.WRITE_CACHE_POLICY_AUTO
-            if flag_has_ram and flag_battery_ok:
-                write_cache_status = Volume.WRITE_CACHE_STATUS_WRITE_BACK
-        elif 'WT' in lsi_cache_setting:
-            write_cache_policy = Volume.WRITE_CACHE_POLICY_WRITE_THROUGH
         else:
             raise LsmError(
                 ErrorNumber.PLUGIN_BUG,
-                "Unknown write cache %s for volume %s" %
+                "Unknown I/O type %s for volume %s" %
                 (lsi_cache_setting, vd_path))
 
+        if flag_has_ram:
+            read_cache_status = Volume.READ_CACHE_STATUS_ENABLED
+            if write_cache_policy == Volume.WRITE_CACHE_POLICY_WRITE_BACK:
+                write_cache_status = Volume.WRITE_CACHE_STATUS_WRITE_BACK
+            elif write_cache_policy == Volume.WRITE_CACHE_POLICY_AUTO:
+                if flag_battery_ok:
+                    write_cache_status = Volume.WRITE_CACHE_STATUS_WRITE_BACK
+
         # TODO(Gris Ge): When 'Block SSD Write Disk Cache Change' of
         #                'Supported Adapter Operations' is 'Yes'
         lsi_disk_cache_setting = vd_prop_info['Disk Cache Policy']
@@ -1162,12 +1165,27 @@ def volume_write_cache_policy_update(self, volume, wcp,
         """
         Depending on "storcli /c0/vX set wrcache=<wt|wb|awb>" command.
         """
-        cmd = [_vd_path_of_lsm_vol(volume), "set"]
+        vd_path = _vd_path_of_lsm_vol(volume)
+        # Check whether we are working on cache I/O which ignore write cache
+        # setting and always cache write.
+        vol_show_output = self._storcli_exec([vd_path, "show", "all"])
+        vd_basic_info = vol_show_output[vd_path][0]
+        lsi_cache_setting = vd_basic_info['Cache']
+        if lsi_cache_setting.endswith('C'):
+            flag_cache_io = True
+        else:
+            flag_cache_io = False
+
+        cmd = [vd_path, "set"]
         if wcp == Volume.WRITE_CACHE_POLICY_WRITE_BACK:
             cmd.append("wrcache=awb")
         elif wcp == Volume.WRITE_CACHE_POLICY_AUTO:
+            if flag_cache_io:
+                self._storcli_exec([vd_path, "set", "iopolicy=Direct"])
             cmd.append("wrcache=wb")
         elif wcp == Volume.WRITE_CACHE_POLICY_WRITE_THROUGH:
+            if flag_cache_io:
+                self._storcli_exec([vd_path, "set", "iopolicy=Direct"])
             cmd.append("wrcache=wt")
         else:
             raise LsmError(ErrorNumber.PLUGIN_BUG,
@@ -1181,8 +1199,9 @@ def volume_read_cache_policy_update(self, volume, rcp,
         storcli always enable read cache and no way to change it
         """
         raise LsmError(ErrorNumber.NO_SUPPORT,
-                       "LSI MegaRAID always enable read cache and refused to "
-                       "change that.")
+                       "MegaRAID always enable read cache and refused to "
+                       "change that. You can change read ahead cache "
+                       "setting via storcli/perccli")
 
     @_handle_errors
     def volume_delete(self, volume, flags=Client.FLAG_RSVD):

From 9502647282e4ccb18aa41933cb8471c61240fa36 Mon Sep 17 00:00:00 2001
From: Gris Ge <fge@redhat.com>
Date: Fri, 8 Dec 2017 19:04:45 +0800
Subject: [PATCH 2/3] MegaRAID plugin: PEP8 clean up

Signed-off-by: Gris Ge <fge@redhat.com>
---
 plugin/megaraid/megaraid.py | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/plugin/megaraid/megaraid.py b/plugin/megaraid/megaraid.py
index 25b900da..c317c11d 100644
--- a/plugin/megaraid/megaraid.py
+++ b/plugin/megaraid/megaraid.py
@@ -85,6 +85,7 @@ def _disk_type_of(disk_show_basic_dict):
 
     return Disk.TYPE_UNKNOWN
 
+
 _DISK_STATE_MAP = {
     'Onln': Disk.STATUS_OK,
     'Offln': Disk.STATUS_ERROR,
@@ -409,7 +410,7 @@ def plugin_info(self, flags=Client.FLAG_RSVD):
 
     @_handle_errors
     def time_out_set(self, ms, flags=Client.FLAG_RSVD):
-        self._tmo_ms = ms # TODO(Gris Ge): Not implemented yet.
+        self._tmo_ms = ms  # TODO(Gris Ge): Not implemented yet.
 
     @_handle_errors
     def time_out_get(self, flags=Client.FLAG_RSVD):
@@ -874,7 +875,8 @@ def _vcr_cap_get(self, mega_sys_path):
         supported_strip_sizes = list(
             min_strip_size * (2 ** i)
             for i in range(
-                0, int(math.log(int_div(max_strip_size, min_strip_size), 2) + 1)))
+                0, int(math.log(int_div(max_strip_size, min_strip_size), 2)
+                       + 1)))
 
         # ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
         # The math above is to generate a list like:

From 0dd64bd71093cf480317251628f66bd4b99ca2a1 Mon Sep 17 00:00:00 2001
From: Gris Ge <fge@redhat.com>
Date: Fri, 8 Dec 2017 19:05:16 +0800
Subject: [PATCH 3/3] MegaRAID plugin: Be consistent on vd_path extraction.

 * Always use _vd_path_of_lsm_vol() to extract private data to vd_path.

Signed-off-by: Gris Ge <fge@redhat.com>
---
 plugin/megaraid/megaraid.py | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/plugin/megaraid/megaraid.py b/plugin/megaraid/megaraid.py
index c317c11d..13c05b52 100644
--- a/plugin/megaraid/megaraid.py
+++ b/plugin/megaraid/megaraid.py
@@ -760,7 +760,7 @@ def volume_raid_info(self, volume, flags=Client.FLAG_RSVD):
                 ErrorNumber.INVALID_ARGUMENT,
                 "Ilegal input volume argument: missing plugin_data property")
 
-        vd_path = volume.plugin_data
+        vd_path = _vd_path_of_lsm_vol(volume)
         vol_show_output = self._storcli_exec([vd_path, "show", "all"])
         vd_basic_info = vol_show_output[vd_path][0]
         vd_id = int(vd_basic_info['DG/VD'].split('/')[-1])