private void flushSnapshot() throws ForeignException {
    if (regions.isEmpty()) {
      // No regions on this RS, we are basically done.
      return;
    }

    monitor.rethrowException();

    // assert that the taskManager is empty.
    if (taskManager.hasTasks()) {
      throw new IllegalStateException(
        "Attempting to take snapshot " + ClientSnapshotDescriptionUtils.toString(snapshot)
          + " but we currently have outstanding tasks");
    }

    // Add all hfiles already existing in region.
    for (HRegion region : regions) {
      // submit one task per region for parallelize by region.
      taskManager.submitTask(new RegionSnapshotTask(region, snapshot, snapshotSkipFlush, monitor));
      monitor.rethrowException();
    }

    // wait for everything to complete.
    LOG.debug("Flush Snapshot Tasks submitted for " + regions.size() + " regions");
    try {
      taskManager.waitForOutstandingTasks();
    } catch (InterruptedException e) {
      LOG.error("got interrupted exception for " + getMemberName());
      throw new ForeignException(getMemberName(), e);
    }
  }
Callable for adding files to snapshot manifest working dir. Ready for multithreading.
hbase-server/src/main/java/org/apache/hadoop/hbase/regionserver/snapshot/FlushSnapshotSubprocedure.java