Skip to content

Commit e66897e

Browse files
author
Kevin Wikant
committed
HDFS-16664. Use correct GenerationStamp when invalidating corrupt block
replicas
1 parent 8774f17 commit e66897e

File tree

2 files changed

+50
-13
lines changed

2 files changed

+50
-13
lines changed

hadoop-hdfs-project/hadoop-hdfs/src/main/java/org/apache/hadoop/hdfs/server/blockmanagement/BlockManager.java

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3730,9 +3730,19 @@ private void invalidateCorruptReplicas(BlockInfo blk, Block reported,
37303730
nodes.toArray(new DatanodeDescriptor[nodes.size()]);
37313731
for (DatanodeDescriptor node : nodesCopy) {
37323732
try {
3733-
if (!invalidateBlock(new BlockToMarkCorrupt(reported, blk, null,
3734-
Reason.ANY), node, numberReplicas)) {
3735-
removedFromBlocksMap = false;
3733+
Long genStamp = corruptReplicas.getCorruptReplicaGenerationStamp(blk, node);
3734+
if (genStamp == null) {
3735+
LOG.warn("CorruptReplicasMap unexpectedly missing generationStamp for datanode {}",
3736+
node.getXferAddr());
3737+
if (!invalidateBlock(new BlockToMarkCorrupt(reported, blk, null,
3738+
Reason.ANY), node, numberReplicas)) {
3739+
removedFromBlocksMap = false;
3740+
}
3741+
} else {
3742+
if (!invalidateBlock(new BlockToMarkCorrupt(reported, blk, genStamp, null,
3743+
Reason.ANY), node, numberReplicas)) {
3744+
removedFromBlocksMap = false;
3745+
}
37363746
}
37373747
} catch (IOException e) {
37383748
if(blockLog.isDebugEnabled()) {

hadoop-hdfs-project/hadoop-hdfs/src/main/java/org/apache/hadoop/hdfs/server/blockmanagement/CorruptReplicasMap.java

Lines changed: 37 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -54,8 +54,18 @@ public enum Reason {
5454
CORRUPTION_REPORTED // client or datanode reported the corruption
5555
}
5656

57-
private final Map<Block, Map<DatanodeDescriptor, Reason>> corruptReplicasMap =
58-
new HashMap<Block, Map<DatanodeDescriptor, Reason>>();
57+
public class CorruptBlockReplica {
58+
public final Reason reason;
59+
public final long generationStamp;
60+
61+
CorruptBlockReplica(Reason reason, long generationStamp) {
62+
this.reason = reason;
63+
this.generationStamp = generationStamp;
64+
}
65+
}
66+
67+
private final Map<Block, Map<DatanodeDescriptor, CorruptBlockReplica>> corruptReplicasMap =
68+
new HashMap<Block, Map<DatanodeDescriptor, CorruptBlockReplica>>();
5969

6070
private final LongAdder totalCorruptBlocks = new LongAdder();
6171
private final LongAdder totalCorruptECBlockGroups = new LongAdder();
@@ -70,9 +80,9 @@ public enum Reason {
7080
*/
7181
void addToCorruptReplicasMap(Block blk, DatanodeDescriptor dn,
7282
String reason, Reason reasonCode, boolean isStriped) {
73-
Map <DatanodeDescriptor, Reason> nodes = corruptReplicasMap.get(blk);
83+
Map <DatanodeDescriptor, CorruptBlockReplica> nodes = corruptReplicasMap.get(blk);
7484
if (nodes == null) {
75-
nodes = new HashMap<DatanodeDescriptor, Reason>();
85+
nodes = new HashMap<DatanodeDescriptor, CorruptBlockReplica>();
7686
corruptReplicasMap.put(blk, nodes);
7787
incrementBlockStat(isStriped);
7888
}
@@ -96,7 +106,7 @@ void addToCorruptReplicasMap(Block blk, DatanodeDescriptor dn,
96106
Server.getRemoteIp(), reasonText);
97107
}
98108
// Add the node or update the reason.
99-
nodes.put(dn, reasonCode);
109+
nodes.put(dn, new CorruptBlockReplica(reasonCode, blk.getGenerationStamp()));
100110
}
101111

102112
/**
@@ -105,7 +115,7 @@ void addToCorruptReplicasMap(Block blk, DatanodeDescriptor dn,
105115
*/
106116
void removeFromCorruptReplicasMap(BlockInfo blk) {
107117
if (corruptReplicasMap != null) {
108-
Map<DatanodeDescriptor, Reason> value = corruptReplicasMap.remove(blk);
118+
Map<DatanodeDescriptor, CorruptBlockReplica> value = corruptReplicasMap.remove(blk);
109119
if (value != null) {
110120
decrementBlockStat(blk.isStriped());
111121
}
@@ -126,13 +136,13 @@ boolean removeFromCorruptReplicasMap(
126136

127137
boolean removeFromCorruptReplicasMap(
128138
BlockInfo blk, DatanodeDescriptor datanode, Reason reason) {
129-
Map <DatanodeDescriptor, Reason> datanodes = corruptReplicasMap.get(blk);
139+
Map <DatanodeDescriptor, CorruptBlockReplica> datanodes = corruptReplicasMap.get(blk);
130140
if (datanodes == null) {
131141
return false;
132142
}
133143

134144
// if reasons can be compared but don't match, return false.
135-
Reason storedReason = datanodes.get(datanode);
145+
Reason storedReason = datanodes.get(datanode).reason;
136146
if (reason != Reason.ANY && storedReason != null &&
137147
reason != storedReason) {
138148
return false;
@@ -172,7 +182,7 @@ private void decrementBlockStat(boolean isStriped) {
172182
* @return collection of nodes. Null if does not exists
173183
*/
174184
Collection<DatanodeDescriptor> getNodes(Block blk) {
175-
Map <DatanodeDescriptor, Reason> nodes = corruptReplicasMap.get(blk);
185+
Map <DatanodeDescriptor, CorruptBlockReplica> nodes = corruptReplicasMap.get(blk);
176186
if (nodes == null)
177187
return null;
178188
return nodes.keySet();
@@ -247,6 +257,23 @@ Set<Block> getCorruptBlocksSet() {
247257
return corruptBlocks;
248258
}
249259

260+
/**
261+
* return the generation stamp of a corrupt replica for a given block
262+
* on a given dn
263+
* @param block block that has corrupted replica
264+
* @param node datanode that contains this corrupted replica
265+
* @return reason
266+
*/
267+
Long getCorruptReplicaGenerationStamp(Block block, DatanodeDescriptor node) {
268+
Long generationStamp = null;
269+
if(corruptReplicasMap.containsKey(block)) {
270+
if (corruptReplicasMap.get(block).containsKey(node)) {
271+
generationStamp = corruptReplicasMap.get(block).get(node).generationStamp;
272+
}
273+
}
274+
return generationStamp;
275+
}
276+
250277
/**
251278
* return the reason about corrupted replica for a given block
252279
* on a given dn
@@ -258,7 +285,7 @@ String getCorruptReason(Block block, DatanodeDescriptor node) {
258285
Reason reason = null;
259286
if(corruptReplicasMap.containsKey(block)) {
260287
if (corruptReplicasMap.get(block).containsKey(node)) {
261-
reason = corruptReplicasMap.get(block).get(node);
288+
reason = corruptReplicasMap.get(block).get(node).reason;
262289
}
263290
}
264291
if (reason != null) {

0 commit comments

Comments
 (0)