Commit f6eaed12 authored by Iustin Pop's avatar Iustin Pop
Browse files

Convert IOErrors for /proc/drbd into our errors

If /proc/drbd can't be opened, this raises an IOError, but all the
error-handling behaviour in backend treats only BlockDeviceErrors. This
creates a plain failure in cluster verify and in other RPC calls.

This patch simply converts EnvironmentErrors into BlockDeviceErrors, and
also changes the RPC result for NV_DRBDLIST and its handling to be able
to show the error. The other RPC calls work by default now, due the
existing error handling.

Reviewed-by: ultrotter
parent 04be7ec6
......@@ -437,9 +437,9 @@ def VerifyNode(what, cluster_name):
if constants.NV_DRBDLIST in what:
try:
used_minors = bdev.DRBD8.GetUsedDevs().keys()
except errors.BlockDeviceError:
except errors.BlockDeviceError, err:
logging.warning("Can't get used minors list", exc_info=True)
used_minors = []
used_minors = str(err)
result[constants.NV_DRBDLIST] = used_minors
return result
......
......@@ -639,11 +639,18 @@ class BaseDRBD(BlockDev):
"""Return data from /proc/drbd.
"""
stat = open(filename, "r")
try:
data = stat.read().splitlines()
finally:
stat.close()
stat = open(filename, "r")
try:
data = stat.read().splitlines()
finally:
stat.close()
except EnvironmentError, err:
if err.errno == errno.ENOENT:
_ThrowError("The file %s cannot be opened, check if the module"
" is loaded (%s)", filename, str(err))
else:
_ThrowError("Can't read the DRBD proc file %s: %s", filename, str(err))
if not data:
_ThrowError("Can't read any data from %s", filename)
return data
......
......@@ -757,15 +757,19 @@ class LUVerifyCluster(LogicalUnit):
# check used drbd list
used_minors = node_result.get(constants.NV_DRBDLIST, [])
for minor, (iname, must_exist) in drbd_map.items():
if minor not in used_minors and must_exist:
feedback_fn(" - ERROR: drbd minor %d of instance %s is not active" %
(minor, iname))
bad = True
for minor in used_minors:
if minor not in drbd_map:
feedback_fn(" - ERROR: unallocated drbd minor %d is in use" % minor)
bad = True
if not isinstance(used_minors, (tuple, list)):
feedback_fn(" - ERROR: cannot parse drbd status file: %s" %
str(used_minors))
else:
for minor, (iname, must_exist) in drbd_map.items():
if minor not in used_minors and must_exist:
feedback_fn(" - ERROR: drbd minor %d of instance %s is not active" %
(minor, iname))
bad = True
for minor in used_minors:
if minor not in drbd_map:
feedback_fn(" - ERROR: unallocated drbd minor %d is in use" % minor)
bad = True
return bad
......
......@@ -106,6 +106,13 @@ class TestDRBD8Status(testutils.GanetiTestCase):
self.proc_data = bdev.DRBD8._GetProcData(filename=proc_data)
self.mass_data = bdev.DRBD8._MassageProcData(self.proc_data)
def testIOErrors(self):
"""Test handling of errors while reading the proc file."""
temp_file = self._CreateTempFile()
os.unlink(temp_file)
self.failUnlessRaises(errors.BlockDeviceError,
bdev.DRBD8._GetProcData, filename=temp_file)
def testMinorNotFound(self):
"""Test not-found-minor in /proc"""
self.failUnless(9 not in self.mass_data)
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment