HDFS-9412. getBlocks occupies FSLock and takes too long to complete. Contributed by He Tianyi.
(cherry picked from commit67523ffcf4
) Conflicts: hadoop-hdfs-project/hadoop-hdfs/src/test/java/org/apache/hadoop/hdfs/TestGetBlocks.java (cherry picked from commita6d0e9e56a
)
This commit is contained in:
parent
84ab382939
commit
7f47d984fa
|
@ -275,6 +275,14 @@ public class BlockManager implements BlockStatsMXBean {
|
|||
* processed again after aquiring lock again.
|
||||
*/
|
||||
private int numBlocksPerIteration;
|
||||
|
||||
/**
|
||||
* Minimum size that a block can be sent to Balancer through getBlocks.
|
||||
* And after HDFS-8824, the small blocks are unused anyway, so there's no
|
||||
* point to send them to balancer.
|
||||
*/
|
||||
private long getBlocksMinBlockSize = -1;
|
||||
|
||||
/**
|
||||
* Progress of the Replication queues initialisation.
|
||||
*/
|
||||
|
@ -370,6 +378,9 @@ public class BlockManager implements BlockStatsMXBean {
|
|||
this.numBlocksPerIteration = conf.getInt(
|
||||
DFSConfigKeys.DFS_BLOCK_MISREPLICATION_PROCESSING_LIMIT,
|
||||
DFSConfigKeys.DFS_BLOCK_MISREPLICATION_PROCESSING_LIMIT_DEFAULT);
|
||||
this.getBlocksMinBlockSize = conf.getLongBytes(
|
||||
DFSConfigKeys.DFS_BALANCER_GETBLOCKS_MIN_BLOCK_SIZE_KEY,
|
||||
DFSConfigKeys.DFS_BALANCER_GETBLOCKS_MIN_BLOCK_SIZE_DEFAULT);
|
||||
this.blockReportLeaseManager = new BlockReportLeaseManager(conf);
|
||||
this.numberOfBytesInFutureBlocks = new AtomicLong();
|
||||
this.inRollBack = isInRollBackMode(NameNode.getStartupOption(conf));
|
||||
|
@ -1083,6 +1094,9 @@ public class BlockManager implements BlockStatsMXBean {
|
|||
while(totalSize<size && iter.hasNext()) {
|
||||
curBlock = iter.next();
|
||||
if(!curBlock.isComplete()) continue;
|
||||
if (curBlock.getNumBytes() < getBlocksMinBlockSize) {
|
||||
continue;
|
||||
}
|
||||
totalSize += addBlock(curBlock, results);
|
||||
}
|
||||
if(totalSize<size) {
|
||||
|
@ -1090,6 +1104,9 @@ public class BlockManager implements BlockStatsMXBean {
|
|||
for(int i=0; i<startBlock&&totalSize<size; i++) {
|
||||
curBlock = iter.next();
|
||||
if(!curBlock.isComplete()) continue;
|
||||
if (curBlock.getNumBytes() < getBlocksMinBlockSize) {
|
||||
continue;
|
||||
}
|
||||
totalSize += addBlock(curBlock, results);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -179,29 +179,19 @@ public class TestGetBlocks {
|
|||
|
||||
final short REPLICATION_FACTOR = (short) 2;
|
||||
final int DEFAULT_BLOCK_SIZE = 1024;
|
||||
final Random r = new Random();
|
||||
|
||||
CONF.setLong(DFSConfigKeys.DFS_BLOCK_SIZE_KEY, DEFAULT_BLOCK_SIZE);
|
||||
CONF.setLong(DFSConfigKeys.DFS_BALANCER_GETBLOCKS_MIN_BLOCK_SIZE_KEY,
|
||||
DEFAULT_BLOCK_SIZE);
|
||||
|
||||
MiniDFSCluster cluster = new MiniDFSCluster.Builder(CONF).numDataNodes(
|
||||
REPLICATION_FACTOR).build();
|
||||
try {
|
||||
cluster.waitActive();
|
||||
|
||||
// create a file with two blocks
|
||||
FileSystem fs = cluster.getFileSystem();
|
||||
FSDataOutputStream out = fs.create(new Path("/tmp.txt"),
|
||||
REPLICATION_FACTOR);
|
||||
byte[] data = new byte[1024];
|
||||
long fileLen = 2 * DEFAULT_BLOCK_SIZE;
|
||||
long bytesToWrite = fileLen;
|
||||
while (bytesToWrite > 0) {
|
||||
r.nextBytes(data);
|
||||
int bytesToWriteNext = (1024 < bytesToWrite) ? 1024
|
||||
: (int) bytesToWrite;
|
||||
out.write(data, 0, bytesToWriteNext);
|
||||
bytesToWrite -= bytesToWriteNext;
|
||||
}
|
||||
out.close();
|
||||
// the third block will not be visible to getBlocks
|
||||
long fileLen = 2 * DEFAULT_BLOCK_SIZE + 1;
|
||||
DFSTestUtil.createFile(cluster.getFileSystem(), new Path("/tmp.txt"),
|
||||
fileLen, REPLICATION_FACTOR, 0L);
|
||||
|
||||
// get blocks & data nodes
|
||||
List<LocatedBlock> locatedBlocks;
|
||||
|
@ -212,7 +202,7 @@ public class TestGetBlocks {
|
|||
DFSUtilClient.getNNAddress(CONF), CONF);
|
||||
locatedBlocks = dfsclient.getNamenode()
|
||||
.getBlockLocations("/tmp.txt", 0, fileLen).getLocatedBlocks();
|
||||
assertEquals(2, locatedBlocks.size());
|
||||
assertEquals(3, locatedBlocks.size());
|
||||
notWritten = false;
|
||||
for (int i = 0; i < 2; i++) {
|
||||
dataNodes = locatedBlocks.get(i).getLocations();
|
||||
|
|
Loading…
Reference in New Issue