17
17
*/
18
18
package org .apache .hadoop .hdfs .server .blockmanagement ;
19
19
20
- import org .apache .hadoop .hdfs . protocol . Block ;
20
+ import org .apache .hadoop .classification . VisibleForTesting ;
21
21
import org .apache .hadoop .hdfs .protocol .ExtendedBlock ;
22
- import org .apache .hadoop .hdfs .util .StripedBlockUtil ;
23
22
import org .apache .hadoop .net .Node ;
24
23
25
- import java .util .ArrayList ;
26
- import java .util .BitSet ;
27
- import java .util .HashMap ;
28
24
import java .util .List ;
29
- import java .util .Map ;
30
25
import java .util .Set ;
31
26
32
27
class ErasureCodingWork extends BlockReconstructionWork {
33
28
private final byte [] liveBlockIndices ;
34
- private final byte [] liveBusyBlockIndices ;
35
29
private final byte [] excludeReconstructedIndices ;
36
30
private final String blockPoolId ;
37
31
@@ -41,13 +35,12 @@ public ErasureCodingWork(String blockPoolId, BlockInfo block,
41
35
List <DatanodeDescriptor > containingNodes ,
42
36
List <DatanodeStorageInfo > liveReplicaStorages ,
43
37
int additionalReplRequired , int priority ,
44
- byte [] liveBlockIndices , byte [] liveBusyBlockIndices ,
38
+ byte [] liveBlockIndices ,
45
39
byte [] excludeReconstrutedIndices ) {
46
40
super (block , bc , srcNodes , containingNodes ,
47
41
liveReplicaStorages , additionalReplRequired , priority );
48
42
this .blockPoolId = blockPoolId ;
49
43
this .liveBlockIndices = liveBlockIndices ;
50
- this .liveBusyBlockIndices = liveBusyBlockIndices ;
51
44
this .excludeReconstructedIndices = excludeReconstrutedIndices ;
52
45
LOG .debug ("Creating an ErasureCodingWork to {} reconstruct " ,
53
46
block );
@@ -77,128 +70,18 @@ void chooseTargets(BlockPlacementPolicy blockplacement,
77
70
setTargets (chosenTargets );
78
71
}
79
72
80
- /**
81
- * @return true if the current source nodes cover all the internal blocks.
82
- * I.e., we only need to have more racks.
83
- */
84
- private boolean hasAllInternalBlocks () {
85
- final BlockInfoStriped block = (BlockInfoStriped ) getBlock ();
86
- if (liveBlockIndices .length
87
- + liveBusyBlockIndices .length < block .getRealTotalBlockNum ()) {
88
- return false ;
89
- }
90
- BitSet bitSet = new BitSet (block .getTotalBlockNum ());
91
- for (byte index : liveBlockIndices ) {
92
- bitSet .set (index );
93
- }
94
- for (byte busyIndex : liveBusyBlockIndices ) {
95
- bitSet .set (busyIndex );
96
- }
97
- for (int i = 0 ; i < block .getRealDataBlockNum (); i ++) {
98
- if (!bitSet .get (i )) {
99
- return false ;
100
- }
101
- }
102
- for (int i = block .getDataBlockNum (); i < block .getTotalBlockNum (); i ++) {
103
- if (!bitSet .get (i )) {
104
- return false ;
105
- }
106
- }
107
- return true ;
108
- }
109
-
110
- /**
111
- * We have all the internal blocks but not enough racks. Thus we do not need
112
- * to do decoding but only simply make an extra copy of an internal block. In
113
- * this scenario, use this method to choose the source datanode for simple
114
- * replication.
115
- * @return The index of the source datanode.
116
- */
117
- private int chooseSource4SimpleReplication () {
118
- Map <String , List <Integer >> map = new HashMap <>();
119
- for (int i = 0 ; i < getSrcNodes ().length ; i ++) {
120
- final String rack = getSrcNodes ()[i ].getNetworkLocation ();
121
- List <Integer > dnList = map .get (rack );
122
- if (dnList == null ) {
123
- dnList = new ArrayList <>();
124
- map .put (rack , dnList );
125
- }
126
- dnList .add (i );
127
- }
128
- List <Integer > max = null ;
129
- for (Map .Entry <String , List <Integer >> entry : map .entrySet ()) {
130
- if (max == null || entry .getValue ().size () > max .size ()) {
131
- max = entry .getValue ();
132
- }
133
- }
134
- assert max != null ;
135
- return max .get (0 );
136
- }
137
-
138
73
@ Override
139
74
void addTaskToDatanode (NumberReplicas numberReplicas ) {
140
75
final DatanodeStorageInfo [] targets = getTargets ();
141
76
assert targets .length > 0 ;
142
77
BlockInfoStriped stripedBlk = (BlockInfoStriped ) getBlock ();
143
-
144
- if (hasNotEnoughRack ()) {
145
- // if we already have all the internal blocks, but not enough racks,
146
- // we only need to replicate one internal block to a new rack
147
- int sourceIndex = chooseSource4SimpleReplication ();
148
- createReplicationWork (sourceIndex , targets [0 ]);
149
- } else if ((numberReplicas .decommissioning () > 0 ||
150
- numberReplicas .liveEnteringMaintenanceReplicas () > 0 ) &&
151
- hasAllInternalBlocks ()) {
152
- List <Integer > leavingServiceSources = findLeavingServiceSources ();
153
- // decommissioningSources.size() should be >= targets.length
154
- final int num = Math .min (leavingServiceSources .size (), targets .length );
155
- for (int i = 0 ; i < num ; i ++) {
156
- createReplicationWork (leavingServiceSources .get (i ), targets [i ]);
157
- }
158
- } else {
159
- targets [0 ].getDatanodeDescriptor ().addBlockToBeErasureCoded (
160
- new ExtendedBlock (blockPoolId , stripedBlk ), getSrcNodes (), targets ,
161
- liveBlockIndices , excludeReconstructedIndices , stripedBlk .getErasureCodingPolicy ());
162
- }
78
+ targets [0 ].getDatanodeDescriptor ().addBlockToBeErasureCoded (
79
+ new ExtendedBlock (blockPoolId , stripedBlk ), getSrcNodes (), targets ,
80
+ liveBlockIndices , excludeReconstructedIndices , stripedBlk .getErasureCodingPolicy ());
163
81
}
164
82
165
- private void createReplicationWork (int sourceIndex ,
166
- DatanodeStorageInfo target ) {
167
- BlockInfoStriped stripedBlk = (BlockInfoStriped ) getBlock ();
168
- final byte blockIndex = liveBlockIndices [sourceIndex ];
169
- final DatanodeDescriptor source = getSrcNodes ()[sourceIndex ];
170
- final long internBlkLen = StripedBlockUtil .getInternalBlockLength (
171
- stripedBlk .getNumBytes (), stripedBlk .getCellSize (),
172
- stripedBlk .getDataBlockNum (), blockIndex );
173
- final Block targetBlk = new Block (stripedBlk .getBlockId () + blockIndex ,
174
- internBlkLen , stripedBlk .getGenerationStamp ());
175
- source .addECBlockToBeReplicated (targetBlk ,
176
- new DatanodeStorageInfo [] {target });
177
- LOG .debug ("Add replication task from source {} to "
178
- + "target {} for EC block {}" , source , target , targetBlk );
179
- }
180
-
181
- private List <Integer > findLeavingServiceSources () {
182
- // Mark the block in normal node.
183
- BlockInfoStriped block = (BlockInfoStriped )getBlock ();
184
- BitSet bitSet = new BitSet (block .getRealTotalBlockNum ());
185
- for (int i = 0 ; i < getSrcNodes ().length ; i ++) {
186
- if (getSrcNodes ()[i ].isInService ()) {
187
- bitSet .set (liveBlockIndices [i ]);
188
- }
189
- }
190
- // If the block is on the node which is decommissioning or
191
- // entering_maintenance, and it doesn't exist on other normal nodes,
192
- // we just add the node into source list.
193
- List <Integer > srcIndices = new ArrayList <>();
194
- for (int i = 0 ; i < getSrcNodes ().length ; i ++) {
195
- if ((getSrcNodes ()[i ].isDecommissionInProgress () ||
196
- (getSrcNodes ()[i ].isEnteringMaintenance () &&
197
- getSrcNodes ()[i ].isAlive ())) &&
198
- !bitSet .get (liveBlockIndices [i ])) {
199
- srcIndices .add (i );
200
- }
201
- }
202
- return srcIndices ;
83
+ @ VisibleForTesting
84
+ public byte [] getExcludeReconstructedIndices () {
85
+ return excludeReconstructedIndices ;
203
86
}
204
87
}
0 commit comments