use of org.apache.hadoop.hdfs.protocol.EncryptionZone in project hadoop by apache.
the class FSDirEncryptionZoneOp method getEZForPath.
/**
* Get the encryption zone for the specified path.
*
* @param fsd fsdirectory
* @param srcArg the path of a file or directory to get the EZ for
* @param pc permission checker to check fs permission
* @return the EZ with file status.
*/
static Map.Entry<EncryptionZone, HdfsFileStatus> getEZForPath(final FSDirectory fsd, final String srcArg, final FSPermissionChecker pc) throws IOException {
final INodesInPath iip;
final EncryptionZone ret;
fsd.readLock();
try {
iip = fsd.resolvePath(pc, srcArg, DirOp.READ);
if (fsd.isPermissionEnabled()) {
fsd.checkPathAccess(pc, iip, FsAction.READ);
}
ret = fsd.ezManager.getEZINodeForPath(iip);
} finally {
fsd.readUnlock();
}
HdfsFileStatus auditStat = fsd.getAuditFileInfo(iip);
return new AbstractMap.SimpleImmutableEntry<>(ret, auditStat);
}
use of org.apache.hadoop.hdfs.protocol.EncryptionZone in project hadoop by apache.
the class FSDirEncryptionZoneOp method getEncryptionKeyInfo.
/**
* If the file is in an encryption zone, we optimistically create an
* EDEK for the file by calling out to the configured KeyProvider.
* Since this typically involves doing an RPC, the fsn lock is yielded.
*
* Since the path can flip-flop between being in an encryption zone and not
* in the meantime, the call MUST re-resolve the IIP and re-check
* preconditions if this method does not return null;
*
* @param fsn the namesystem.
* @param iip the inodes for the path
* @param supportedVersions client's supported versions
* @return EncryptionKeyInfo if the path is in an EZ, else null
*/
static EncryptionKeyInfo getEncryptionKeyInfo(FSNamesystem fsn, INodesInPath iip, CryptoProtocolVersion[] supportedVersions) throws IOException {
FSDirectory fsd = fsn.getFSDirectory();
// Nothing to do if the path is not within an EZ
final EncryptionZone zone = getEZForPath(fsd, iip);
if (zone == null) {
EncryptionFaultInjector.getInstance().startFileNoKey();
return null;
}
CryptoProtocolVersion protocolVersion = fsn.chooseProtocolVersion(zone, supportedVersions);
CipherSuite suite = zone.getSuite();
String ezKeyName = zone.getKeyName();
Preconditions.checkNotNull(protocolVersion);
Preconditions.checkNotNull(suite);
Preconditions.checkArgument(!suite.equals(CipherSuite.UNKNOWN), "Chose an UNKNOWN CipherSuite!");
Preconditions.checkNotNull(ezKeyName);
// Generate EDEK while not holding the fsn lock.
fsn.writeUnlock();
try {
EncryptionFaultInjector.getInstance().startFileBeforeGenerateKey();
return new EncryptionKeyInfo(protocolVersion, suite, ezKeyName, generateEncryptedDataEncryptionKey(fsd, ezKeyName));
} finally {
fsn.writeLock();
EncryptionFaultInjector.getInstance().startFileAfterGenerateKey();
}
}
use of org.apache.hadoop.hdfs.protocol.EncryptionZone in project hadoop by apache.
the class FSNamesystem method getEZForPath.
/**
* Get the encryption zone for the specified path.
*
* @param srcArg the path of a file or directory to get the EZ for.
* @return the EZ of the of the path or null if none.
* @throws AccessControlException if the caller is not the superuser.
* @throws UnresolvedLinkException if the path can't be resolved.
*/
EncryptionZone getEZForPath(final String srcArg) throws AccessControlException, UnresolvedLinkException, IOException {
final String operationName = "getEZForPath";
HdfsFileStatus resultingStat = null;
boolean success = false;
EncryptionZone encryptionZone;
final FSPermissionChecker pc = getPermissionChecker();
checkOperation(OperationCategory.READ);
readLock();
try {
checkOperation(OperationCategory.READ);
Entry<EncryptionZone, HdfsFileStatus> ezForPath = FSDirEncryptionZoneOp.getEZForPath(dir, srcArg, pc);
success = true;
resultingStat = ezForPath.getValue();
encryptionZone = ezForPath.getKey();
} catch (AccessControlException ace) {
logAuditEvent(success, operationName, srcArg, null, resultingStat);
throw ace;
} finally {
readUnlock(operationName);
}
logAuditEvent(success, operationName, srcArg, null, resultingStat);
return encryptionZone;
}
use of org.apache.hadoop.hdfs.protocol.EncryptionZone in project hadoop by apache.
the class TestEncryptionZones method testSnapshotsOnEncryptionZones.
/**
* Test correctness of successive snapshot creation and deletion
* on a system with encryption zones.
*/
@Test
public void testSnapshotsOnEncryptionZones() throws Exception {
final String TEST_KEY2 = "testkey2";
DFSTestUtil.createKey(TEST_KEY2, cluster, conf);
final int len = 8196;
final Path zoneParent = new Path("/zones");
final Path zone = new Path(zoneParent, "zone");
final Path zoneFile = new Path(zone, "zoneFile");
fsWrapper.mkdir(zone, FsPermission.getDirDefault(), true);
dfsAdmin.allowSnapshot(zoneParent);
dfsAdmin.createEncryptionZone(zone, TEST_KEY, NO_TRASH);
DFSTestUtil.createFile(fs, zoneFile, len, (short) 1, 0xFEED);
String contents = DFSTestUtil.readFile(fs, zoneFile);
final Path snap1 = fs.createSnapshot(zoneParent, "snap1");
final Path snap1Zone = new Path(snap1, zone.getName());
assertEquals("Got unexpected ez path", zone.toString(), dfsAdmin.getEncryptionZoneForPath(snap1Zone).getPath().toString());
// Now delete the encryption zone, recreate the dir, and take another
// snapshot
fsWrapper.delete(zone, true);
fsWrapper.mkdir(zone, FsPermission.getDirDefault(), true);
final Path snap2 = fs.createSnapshot(zoneParent, "snap2");
final Path snap2Zone = new Path(snap2, zone.getName());
assertNull("Expected null ez path", dfsAdmin.getEncryptionZoneForPath(snap2Zone));
// Create the encryption zone again
dfsAdmin.createEncryptionZone(zone, TEST_KEY2, NO_TRASH);
final Path snap3 = fs.createSnapshot(zoneParent, "snap3");
final Path snap3Zone = new Path(snap3, zone.getName());
// Check that snap3's EZ has the correct settings
EncryptionZone ezSnap3 = dfsAdmin.getEncryptionZoneForPath(snap3Zone);
assertEquals("Got unexpected ez path", zone.toString(), ezSnap3.getPath().toString());
assertEquals("Unexpected ez key", TEST_KEY2, ezSnap3.getKeyName());
// Check that older snapshots still have the old EZ settings
EncryptionZone ezSnap1 = dfsAdmin.getEncryptionZoneForPath(snap1Zone);
assertEquals("Got unexpected ez path", zone.toString(), ezSnap1.getPath().toString());
assertEquals("Unexpected ez key", TEST_KEY, ezSnap1.getKeyName());
// Check that listEZs only shows the current filesystem state
ArrayList<EncryptionZone> listZones = Lists.newArrayList();
RemoteIterator<EncryptionZone> it = dfsAdmin.listEncryptionZones();
while (it.hasNext()) {
listZones.add(it.next());
}
for (EncryptionZone z : listZones) {
System.out.println(z);
}
assertEquals("Did not expect additional encryption zones!", 1, listZones.size());
EncryptionZone listZone = listZones.get(0);
assertEquals("Got unexpected ez path", zone.toString(), listZone.getPath().toString());
assertEquals("Unexpected ez key", TEST_KEY2, listZone.getKeyName());
// Verify contents of the snapshotted file
final Path snapshottedZoneFile = new Path(snap1.toString() + "/" + zone.getName() + "/" + zoneFile.getName());
assertEquals("Contents of snapshotted file have changed unexpectedly", contents, DFSTestUtil.readFile(fs, snapshottedZoneFile));
// Now delete the snapshots out of order and verify the zones are still
// correct
fs.deleteSnapshot(zoneParent, snap2.getName());
assertEquals("Got unexpected ez path", zone.toString(), dfsAdmin.getEncryptionZoneForPath(snap1Zone).getPath().toString());
assertEquals("Got unexpected ez path", zone.toString(), dfsAdmin.getEncryptionZoneForPath(snap3Zone).getPath().toString());
fs.deleteSnapshot(zoneParent, snap1.getName());
assertEquals("Got unexpected ez path", zone.toString(), dfsAdmin.getEncryptionZoneForPath(snap3Zone).getPath().toString());
}
use of org.apache.hadoop.hdfs.protocol.EncryptionZone in project hadoop by apache.
the class TestEncryptionZones method assertZonePresent.
/**
* Checks that an encryption zone with the specified keyName and path (if not
* null) is present.
*
* @throws IOException if a matching zone could not be found
*/
public void assertZonePresent(String keyName, String path) throws IOException {
final RemoteIterator<EncryptionZone> it = dfsAdmin.listEncryptionZones();
boolean match = false;
while (it.hasNext()) {
EncryptionZone zone = it.next();
boolean matchKey = (keyName == null);
boolean matchPath = (path == null);
if (keyName != null && zone.getKeyName().equals(keyName)) {
matchKey = true;
}
if (path != null && zone.getPath().equals(path)) {
matchPath = true;
}
if (matchKey && matchPath) {
match = true;
break;
}
}
assertTrue("Did not find expected encryption zone with keyName " + keyName + " path " + path, match);
}
Aggregations