YARN-644: Basic null check is not performed on passed in arguments before using them in ContainerManagerImpl.startContainer

This commit is contained in:
Robert (Bobby) Evans 2015-05-08 11:09:29 -05:00
parent dc2b2ae31f
commit bcf2890502
4 changed files with 122 additions and 1 deletions

View File

@ -113,6 +113,9 @@ Release 2.8.0 - UNRELEASED
IMPROVEMENTS IMPROVEMENTS
YARN-644. Basic null check is not performed on passed in arguments before
using them in ContainerManagerImpl.startContainer (Varun Saxena via bobby)
YARN-1880. Cleanup TestApplicationClientProtocolOnHA YARN-1880. Cleanup TestApplicationClientProtocolOnHA
(ozawa via harsh) (ozawa via harsh)

View File

@ -151,6 +151,10 @@ public class ContainerManagerImpl extends CompositeService implements
private static final Log LOG = LogFactory.getLog(ContainerManagerImpl.class); private static final Log LOG = LogFactory.getLog(ContainerManagerImpl.class);
static final String INVALID_NMTOKEN_MSG = "Invalid NMToken";
static final String INVALID_CONTAINERTOKEN_MSG =
"Invalid ContainerToken";
final Context context; final Context context;
private final ContainersMonitor containersMonitor; private final ContainersMonitor containersMonitor;
private Server server; private Server server;
@ -641,6 +645,9 @@ public class ContainerManagerImpl extends CompositeService implements
protected void authorizeUser(UserGroupInformation remoteUgi, protected void authorizeUser(UserGroupInformation remoteUgi,
NMTokenIdentifier nmTokenIdentifier) throws YarnException { NMTokenIdentifier nmTokenIdentifier) throws YarnException {
if (nmTokenIdentifier == null) {
throw RPCUtil.getRemoteException(INVALID_NMTOKEN_MSG);
}
if (!remoteUgi.getUserName().equals( if (!remoteUgi.getUserName().equals(
nmTokenIdentifier.getApplicationAttemptId().toString())) { nmTokenIdentifier.getApplicationAttemptId().toString())) {
throw RPCUtil.getRemoteException("Expected applicationAttemptId: " throw RPCUtil.getRemoteException("Expected applicationAttemptId: "
@ -658,7 +665,12 @@ public class ContainerManagerImpl extends CompositeService implements
@VisibleForTesting @VisibleForTesting
protected void authorizeStartRequest(NMTokenIdentifier nmTokenIdentifier, protected void authorizeStartRequest(NMTokenIdentifier nmTokenIdentifier,
ContainerTokenIdentifier containerTokenIdentifier) throws YarnException { ContainerTokenIdentifier containerTokenIdentifier) throws YarnException {
if (nmTokenIdentifier == null) {
throw RPCUtil.getRemoteException(INVALID_NMTOKEN_MSG);
}
if (containerTokenIdentifier == null) {
throw RPCUtil.getRemoteException(INVALID_CONTAINERTOKEN_MSG);
}
ContainerId containerId = containerTokenIdentifier.getContainerID(); ContainerId containerId = containerTokenIdentifier.getContainerID();
String containerIDStr = containerId.toString(); String containerIDStr = containerId.toString();
boolean unauthorized = false; boolean unauthorized = false;
@ -717,6 +729,10 @@ public class ContainerManagerImpl extends CompositeService implements
for (StartContainerRequest request : requests.getStartContainerRequests()) { for (StartContainerRequest request : requests.getStartContainerRequests()) {
ContainerId containerId = null; ContainerId containerId = null;
try { try {
if (request.getContainerToken() == null ||
request.getContainerToken().getIdentifier() == null) {
throw new IOException(INVALID_CONTAINERTOKEN_MSG);
}
ContainerTokenIdentifier containerTokenIdentifier = ContainerTokenIdentifier containerTokenIdentifier =
BuilderUtils.newContainerTokenIdentifier(request.getContainerToken()); BuilderUtils.newContainerTokenIdentifier(request.getContainerToken());
verifyAndGetContainerTokenIdentifier(request.getContainerToken(), verifyAndGetContainerTokenIdentifier(request.getContainerToken(),
@ -946,6 +962,9 @@ public class ContainerManagerImpl extends CompositeService implements
new HashMap<ContainerId, SerializedException>(); new HashMap<ContainerId, SerializedException>();
UserGroupInformation remoteUgi = getRemoteUgi(); UserGroupInformation remoteUgi = getRemoteUgi();
NMTokenIdentifier identifier = selectNMTokenIdentifier(remoteUgi); NMTokenIdentifier identifier = selectNMTokenIdentifier(remoteUgi);
if (identifier == null) {
throw RPCUtil.getRemoteException(INVALID_NMTOKEN_MSG);
}
for (ContainerId id : requests.getContainerIds()) { for (ContainerId id : requests.getContainerIds()) {
try { try {
stopContainerInternal(identifier, id); stopContainerInternal(identifier, id);
@ -1001,6 +1020,9 @@ public class ContainerManagerImpl extends CompositeService implements
new HashMap<ContainerId, SerializedException>(); new HashMap<ContainerId, SerializedException>();
UserGroupInformation remoteUgi = getRemoteUgi(); UserGroupInformation remoteUgi = getRemoteUgi();
NMTokenIdentifier identifier = selectNMTokenIdentifier(remoteUgi); NMTokenIdentifier identifier = selectNMTokenIdentifier(remoteUgi);
if (identifier == null) {
throw RPCUtil.getRemoteException(INVALID_NMTOKEN_MSG);
}
for (ContainerId id : request.getContainerIds()) { for (ContainerId id : request.getContainerIds()) {
try { try {
ContainerStatus status = getContainerStatusInternal(id, identifier); ContainerStatus status = getContainerStatusInternal(id, identifier);
@ -1041,6 +1063,9 @@ public class ContainerManagerImpl extends CompositeService implements
protected void authorizeGetAndStopContainerRequest(ContainerId containerId, protected void authorizeGetAndStopContainerRequest(ContainerId containerId,
Container container, boolean stopRequest, NMTokenIdentifier identifier) Container container, boolean stopRequest, NMTokenIdentifier identifier)
throws YarnException { throws YarnException {
if (identifier == null) {
throw RPCUtil.getRemoteException(INVALID_NMTOKEN_MSG);
}
/* /*
* For get/stop container status; we need to verify that 1) User (NMToken) * For get/stop container status; we need to verify that 1) User (NMToken)
* application attempt only has started container. 2) Requested containerId * application attempt only has started container. 2) Requested containerId

View File

@ -230,6 +230,12 @@ public abstract class BaseContainerManagerTest {
ByteBuffer.wrap("AuxServiceMetaData2".getBytes())); ByteBuffer.wrap("AuxServiceMetaData2".getBytes()));
return serviceData; return serviceData;
} }
@Override
protected NMTokenIdentifier selectNMTokenIdentifier(
UserGroupInformation remoteUgi) {
return new NMTokenIdentifier();
}
}; };
} }

View File

@ -45,6 +45,9 @@ import org.apache.hadoop.yarn.api.protocolrecords.StartContainersRequest;
import org.apache.hadoop.yarn.api.protocolrecords.StartContainersResponse; import org.apache.hadoop.yarn.api.protocolrecords.StartContainersResponse;
import org.apache.hadoop.yarn.api.protocolrecords.StopContainersRequest; import org.apache.hadoop.yarn.api.protocolrecords.StopContainersRequest;
import org.apache.hadoop.yarn.api.protocolrecords.StopContainersResponse; import org.apache.hadoop.yarn.api.protocolrecords.StopContainersResponse;
import org.apache.hadoop.yarn.api.protocolrecords.impl.pb.GetContainerStatusesRequestPBImpl;
import org.apache.hadoop.yarn.api.protocolrecords.impl.pb.StartContainersRequestPBImpl;
import org.apache.hadoop.yarn.api.protocolrecords.impl.pb.StopContainersRequestPBImpl;
import org.apache.hadoop.yarn.api.records.ApplicationAttemptId; import org.apache.hadoop.yarn.api.records.ApplicationAttemptId;
import org.apache.hadoop.yarn.api.records.ApplicationId; import org.apache.hadoop.yarn.api.records.ApplicationId;
import org.apache.hadoop.yarn.api.records.ContainerExitStatus; import org.apache.hadoop.yarn.api.records.ContainerExitStatus;
@ -83,6 +86,7 @@ import org.apache.hadoop.yarn.util.ConverterUtils;
import org.junit.Assert; import org.junit.Assert;
import org.junit.Before; import org.junit.Before;
import org.junit.Test; import org.junit.Test;
import org.mockito.Mockito;
public class TestContainerManager extends BaseContainerManagerTest { public class TestContainerManager extends BaseContainerManagerTest {
@ -792,6 +796,89 @@ public class TestContainerManager extends BaseContainerManagerTest {
.contains("The auxService:" + serviceName + " does not exist")); .contains("The auxService:" + serviceName + " does not exist"));
} }
/* Test added to verify fix in YARN-644 */
@Test
public void testNullTokens() throws Exception {
ContainerManagerImpl cMgrImpl =
new ContainerManagerImpl(context, exec, delSrvc, nodeStatusUpdater,
metrics, new ApplicationACLsManager(conf), dirsHandler);
String strExceptionMsg = "";
try {
cMgrImpl.authorizeStartRequest(null, new ContainerTokenIdentifier());
} catch(YarnException ye) {
strExceptionMsg = ye.getMessage();
}
Assert.assertEquals(strExceptionMsg,
ContainerManagerImpl.INVALID_NMTOKEN_MSG);
strExceptionMsg = "";
try {
cMgrImpl.authorizeStartRequest(new NMTokenIdentifier(), null);
} catch(YarnException ye) {
strExceptionMsg = ye.getMessage();
}
Assert.assertEquals(strExceptionMsg,
ContainerManagerImpl.INVALID_CONTAINERTOKEN_MSG);
strExceptionMsg = "";
try {
cMgrImpl.authorizeGetAndStopContainerRequest(null, null, true, null);
} catch(YarnException ye) {
strExceptionMsg = ye.getMessage();
}
Assert.assertEquals(strExceptionMsg,
ContainerManagerImpl.INVALID_NMTOKEN_MSG);
strExceptionMsg = "";
try {
cMgrImpl.authorizeUser(null, null);
} catch(YarnException ye) {
strExceptionMsg = ye.getMessage();
}
Assert.assertEquals(strExceptionMsg,
ContainerManagerImpl.INVALID_NMTOKEN_MSG);
ContainerManagerImpl spyContainerMgr = Mockito.spy(cMgrImpl);
UserGroupInformation ugInfo = UserGroupInformation.createRemoteUser("a");
Mockito.when(spyContainerMgr.getRemoteUgi()).thenReturn(ugInfo);
Mockito.when(spyContainerMgr.
selectNMTokenIdentifier(ugInfo)).thenReturn(null);
strExceptionMsg = "";
try {
spyContainerMgr.stopContainers(new StopContainersRequestPBImpl());
} catch(YarnException ye) {
strExceptionMsg = ye.getMessage();
}
Assert.assertEquals(strExceptionMsg,
ContainerManagerImpl.INVALID_NMTOKEN_MSG);
strExceptionMsg = "";
try {
spyContainerMgr.getContainerStatuses(
new GetContainerStatusesRequestPBImpl());
} catch(YarnException ye) {
strExceptionMsg = ye.getMessage();
}
Assert.assertEquals(strExceptionMsg,
ContainerManagerImpl.INVALID_NMTOKEN_MSG);
Mockito.doNothing().when(spyContainerMgr).authorizeUser(ugInfo, null);
List<StartContainerRequest> reqList
= new ArrayList<StartContainerRequest>();
reqList.add(StartContainerRequest.newInstance(null, null));
StartContainersRequest reqs = new StartContainersRequestPBImpl();
reqs.setStartContainerRequests(reqList);
strExceptionMsg = "";
try {
spyContainerMgr.startContainers(reqs);
} catch(YarnException ye) {
strExceptionMsg = ye.getCause().getMessage();
}
Assert.assertEquals(strExceptionMsg,
ContainerManagerImpl.INVALID_CONTAINERTOKEN_MSG);
}
public static Token createContainerToken(ContainerId cId, long rmIdentifier, public static Token createContainerToken(ContainerId cId, long rmIdentifier,
NodeId nodeId, String user, NodeId nodeId, String user,
NMContainerTokenSecretManager containerTokenSecretManager) NMContainerTokenSecretManager containerTokenSecretManager)