datanode = DataNode.createInterDataNodeProtocolProxy(
id, getConf(), socketTimeout);
datanodeProxies.add(datanode);
}
throwIfAfterTime(deadline);
BlockRecoveryInfo info = datanode.startBlockRecovery(namespaceId, block);
if (info == null) {
LOG.info("No block metadata found for block " + block + " on datanode "
+ id);
continue;
}
if (info.getBlock().getGenerationStamp() < block.getGenerationStamp()) {
LOG.info("Only old generation stamp " + info.getBlock().getGenerationStamp()
+ " found on datanode " + id + " (needed block=" +
block + ")");
continue;
}
blockRecords.add(new BlockRecord(id, datanode, info));
if (info.wasRecoveredOnStartup()) {
rwrCount++;
} else {
rbwCount++;
}
} catch (BlockRecoveryTimeoutException e) {
throw e;
} catch (IOException e) {
++errorCount;
InterDatanodeProtocol.LOG.warn(
"Failed to getBlockMetaDataInfo for block (=" + block
+ ") from datanode (=" + id + ")", e);
}
}
// If we *only* have replicas from post-DN-restart, then we should
// include them in determining length. Otherwise they might cause us
// to truncate too short.
boolean shouldRecoverRwrs = (rbwCount == 0);
List<BlockRecord> syncList = new ArrayList<BlockRecord>();
long minlength = Long.MAX_VALUE;
for (BlockRecord record : blockRecords) {
BlockRecoveryInfo info = record.info;
assert (info != null && info.getBlock().getGenerationStamp() >= block.getGenerationStamp());
if (!shouldRecoverRwrs && info.wasRecoveredOnStartup()) {
LOG.info("Not recovering replica " + record + " since it was recovered on "
+ "startup and we have better replicas");
continue;
}
if (keepLength) {
if (info.getBlock().getNumBytes() == block.getNumBytes()) {
syncList.add(record);
}
} else {
syncList.add(record);
if (info.getBlock().getNumBytes() < minlength) {
minlength = info.getBlock().getNumBytes();
}
}
}
if (syncList.isEmpty() && errorCount > 0) {