From d9b6103f8f63f66c254a7bd3a423a2a5fb6672e3 Mon Sep 17 00:00:00 2001 From: Boris Shkolnik Date: Thu, 13 May 2010 20:52:59 +0000 Subject: [PATCH] HADOOP-6600. mechanism for authorization check for inter-server protocols git-svn-id: https://svn.apache.org/repos/asf/hadoop/common/trunk@944012 13f79535-47bb-0310-9956-ffa450edef68 --- CHANGES.txt | 3 +++ src/java/org/apache/hadoop/ipc/Client.java | 2 +- src/java/org/apache/hadoop/ipc/Server.java | 2 +- .../apache/hadoop/security/KerberosInfo.java | 3 ++- .../ServiceAuthorizationManager.java | 21 +++++++++++++++---- .../apache/hadoop/ipc/MiniRPCBenchmark.java | 3 ++- .../org/apache/hadoop/ipc/TestSaslRPC.java | 3 ++- 7 files changed, 28 insertions(+), 9 deletions(-) diff --git a/CHANGES.txt b/CHANGES.txt index c3cd8d69457..828cdf88865 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -4,6 +4,9 @@ Trunk (unreleased changes) IMPROVEMENTS + HADOOP-6600. mechanism for authorization check for inter-server + protocols. (boryas) + HADOOP-6623. Add StringUtils.split for non-escaped single-character separator. (Todd Lipcon via tomwhite) diff --git a/src/java/org/apache/hadoop/ipc/Client.java b/src/java/org/apache/hadoop/ipc/Client.java index a7c25d3b9ce..2de3f9804bf 100644 --- a/src/java/org/apache/hadoop/ipc/Client.java +++ b/src/java/org/apache/hadoop/ipc/Client.java @@ -253,7 +253,7 @@ public Connection(ConnectionId remoteId) throws IOException { } KerberosInfo krbInfo = protocol.getAnnotation(KerberosInfo.class); if (krbInfo != null) { - String serverKey = krbInfo.value(); + String serverKey = krbInfo.serverPrincipal(); if (serverKey != null) { serverPrincipal = conf.get(serverKey); } diff --git a/src/java/org/apache/hadoop/ipc/Server.java b/src/java/org/apache/hadoop/ipc/Server.java index cf6299f10bb..9339ca5e919 100644 --- a/src/java/org/apache/hadoop/ipc/Server.java +++ b/src/java/org/apache/hadoop/ipc/Server.java @@ -1615,7 +1615,7 @@ public void authorize(UserGroupInformation user, throw new AuthorizationException("Unknown protocol: " + connection.getProtocol()); } - ServiceAuthorizationManager.authorize(user, protocol); + ServiceAuthorizationManager.authorize(user, protocol, getConf()); } } diff --git a/src/java/org/apache/hadoop/security/KerberosInfo.java b/src/java/org/apache/hadoop/security/KerberosInfo.java index e8b574786a1..15236e7be47 100644 --- a/src/java/org/apache/hadoop/security/KerberosInfo.java +++ b/src/java/org/apache/hadoop/security/KerberosInfo.java @@ -27,5 +27,6 @@ @Target(ElementType.TYPE) public @interface KerberosInfo { /** Key for getting server's Kerberos principal name from Configuration */ - String value(); + String serverPrincipal(); + String clientPrincipal() default ""; } diff --git a/src/java/org/apache/hadoop/security/authorize/ServiceAuthorizationManager.java b/src/java/org/apache/hadoop/security/authorize/ServiceAuthorizationManager.java index 3cf04b99450..dbb29b5e3ad 100644 --- a/src/java/org/apache/hadoop/security/authorize/ServiceAuthorizationManager.java +++ b/src/java/org/apache/hadoop/security/authorize/ServiceAuthorizationManager.java @@ -24,6 +24,7 @@ import org.apache.commons.logging.LogFactory; import org.apache.hadoop.conf.Configuration; import org.apache.hadoop.fs.CommonConfigurationKeys; +import org.apache.hadoop.security.KerberosInfo; import org.apache.hadoop.security.UserGroupInformation; /** @@ -62,18 +63,30 @@ public class ServiceAuthorizationManager { * @throws AuthorizationException on authorization failure */ public static void authorize(UserGroupInformation user, - Class protocol + Class protocol, + Configuration conf ) throws AuthorizationException { AccessControlList acl = protocolToAcl.get(protocol); if (acl == null) { throw new AuthorizationException("Protocol " + protocol + " is not known."); } - if (!acl.isUserAllowed(user)) { + + // get client principal key to verify (if available) + KerberosInfo krbInfo = protocol.getAnnotation(KerberosInfo.class); + String clientPrincipal = null; + if (krbInfo != null) { + String clientKey = krbInfo.clientPrincipal(); + if (clientKey != null && !clientKey.equals("")) { + clientPrincipal = conf.get(clientKey); + } + } + if((clientPrincipal != null && !clientPrincipal.equals(user.getUserName())) || + !acl.isUserAllowed(user)) { auditLOG.warn(AUTHZ_FAILED_FOR + user + " for protocol="+protocol); throw new AuthorizationException("User " + user + - " is not authorized for protocol " + - protocol); + " is not authorized for protocol " + + protocol); } auditLOG.info(AUTHZ_SUCCESSFULL_FOR + user + " for protocol="+protocol); } diff --git a/src/test/core/org/apache/hadoop/ipc/MiniRPCBenchmark.java b/src/test/core/org/apache/hadoop/ipc/MiniRPCBenchmark.java index e8b0d02cf95..fa429e4a012 100644 --- a/src/test/core/org/apache/hadoop/ipc/MiniRPCBenchmark.java +++ b/src/test/core/org/apache/hadoop/ipc/MiniRPCBenchmark.java @@ -101,7 +101,8 @@ protected TestDelegationTokenSelector() { } } - @KerberosInfo(USER_NAME_KEY) + @KerberosInfo( + serverPrincipal=USER_NAME_KEY) @TokenInfo(TestDelegationTokenSelector.class) public static interface MiniProtocol extends VersionedProtocol { public static final long versionID = 1L; diff --git a/src/test/core/org/apache/hadoop/ipc/TestSaslRPC.java b/src/test/core/org/apache/hadoop/ipc/TestSaslRPC.java index 3e9fea3280e..44a38b9d95a 100644 --- a/src/test/core/org/apache/hadoop/ipc/TestSaslRPC.java +++ b/src/test/core/org/apache/hadoop/ipc/TestSaslRPC.java @@ -162,7 +162,8 @@ public Token selectToken(Text service, } } - @KerberosInfo(SERVER_PRINCIPAL_KEY) + @KerberosInfo( + serverPrincipal = SERVER_PRINCIPAL_KEY) @TokenInfo(TestTokenSelector.class) public interface TestSaslProtocol extends TestRPC.TestProtocol { public AuthenticationMethod getAuthMethod() throws IOException;