Addendum patch for HDFS-9781. FsDatasetImpl#getBlockReports can occasionally throw NullPointerException. Contributed by Manoj Govindassamy.

This commit is contained in:
Xiao Chen 2016-09-09 10:52:05 -07:00
parent d4d076876a
commit a0b0383677

View File

@ -589,20 +589,21 @@ public void testRemoveVolumeBeingWritten() throws Exception {
// Will write and remove on dn0.
final ExtendedBlock eb = new ExtendedBlock(BLOCK_POOL_IDS[0], 0);
final CountDownLatch startFinalizeLatch = new CountDownLatch(1);
final CountDownLatch brReceivedLatch = new CountDownLatch(1);
final CountDownLatch volRemovedLatch = new CountDownLatch(1);
final CountDownLatch blockReportReceivedLatch = new CountDownLatch(1);
final CountDownLatch volRemoveStartedLatch = new CountDownLatch(1);
final CountDownLatch volRemoveCompletedLatch = new CountDownLatch(1);
class BlockReportThread extends Thread {
public void run() {
// Lets wait for the volume remove process to start
try {
volRemovedLatch.await();
volRemoveStartedLatch.await();
} catch (Exception e) {
LOG.info("Unexpected exception when waiting for vol removal:", e);
}
LOG.info("Getting block report");
dataset.getBlockReports(eb.getBlockPoolId());
LOG.info("Successfully received block report");
brReceivedLatch.countDown();
blockReportReceivedLatch.countDown();
}
}
@ -623,7 +624,7 @@ public void run() {
}
// Lets wait for the other thread finish getting block report
brReceivedLatch.await();
blockReportReceivedLatch.await();
dataset.finalizeBlock(eb);
LOG.info("FinalizeBlock finished");
@ -633,34 +634,58 @@ public void run() {
}
}
ResponderThread res = new ResponderThread();
res.start();
startFinalizeLatch.await();
// Verify if block report can be received
// when volume is being removed
final BlockReportThread brt = new BlockReportThread();
brt.start();
Set<File> volumesToRemove = new HashSet<>();
volumesToRemove.add(
StorageLocation.parse(dataset.getVolume(eb).getBasePath()).getFile());
/**
* TODO: {@link FsDatasetImpl#removeVolumes(Set, boolean)} is throwing
* IllegalMonitorStateException when there is a parallel reader/writer
* to the volume. Remove below try/catch block after fixing HDFS-10830.
*/
try {
LOG.info("Removing volume " + volumesToRemove);
dataset.removeVolumes(volumesToRemove, true);
} catch (Exception e) {
LOG.info("Unexpected issue while removing volume: ", e);
} finally {
volRemovedLatch.countDown();
class VolRemoveThread extends Thread {
public void run() {
try {
Set<File> volumesToRemove = new HashSet<>();
volumesToRemove.add(StorageLocation.parse(
dataset.getVolume(eb).getBasePath()).getFile());
/**
* TODO: {@link FsDatasetImpl#removeVolumes(Set, boolean)} is throwing
* IllegalMonitorStateException when there is a parallel reader/writer
* to the volume. Remove below exception handling block after fixing
* HDFS-10830.
*/
LOG.info("Removing volume " + volumesToRemove);
dataset.removeVolumes(volumesToRemove, true);
volRemoveCompletedLatch.countDown();
LOG.info("Removed volume " + volumesToRemove);
} catch (Exception e) {
LOG.info("Unexpected issue while removing volume: ", e);
volRemoveCompletedLatch.countDown();
}
}
}
LOG.info("Volumes removed");
brReceivedLatch.await();
// Start the volume write operation
ResponderThread responderThread = new ResponderThread();
responderThread.start();
startFinalizeLatch.await();
// Start the block report get operation
final BlockReportThread blockReportThread = new BlockReportThread();
blockReportThread.start();
// Start the volume remove operation
VolRemoveThread volRemoveThread = new VolRemoveThread();
volRemoveThread.start();
// Let volume write and remove operation be
// blocked for few seconds
Thread.sleep(2000);
// Signal block report receiver and volume writer
// thread to complete their operations so that vol
// remove can proceed
volRemoveStartedLatch.countDown();
// Verify if block report can be received
// when volume is in use and also being removed
blockReportReceivedLatch.await();
// Verify if volume can be removed safely when there
// are read/write operation in-progress
volRemoveCompletedLatch.await();
}
/**