You are viewing a plain text version of this content. The canonical link for it is here.
Posted to common-commits@hadoop.apache.org by el...@apache.org on 2012/05/04 23:58:45 UTC
svn commit: r1334216 - in
/hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main:
java/org/apache/hadoop/http/ java/org/apache/hadoop/security/
packages/templates/conf/
Author: eli
Date: Fri May 4 21:58:44 2012
New Revision: 1334216
URL: http://svn.apache.org/viewvc?rev=1334216&view=rev
Log:
HDFS-2617. Replaced Kerberized SSL for image transfer and fsck with SPNEGO-based solution. Contributed by Jakob Homan, Alejandro Abdelnur, and Aaron T. Myers
Removed:
hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/security/Krb5AndCertsSslSocketConnector.java
Modified:
hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/http/HttpServer.java
hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/security/SecurityUtil.java
hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/packages/templates/conf/hdfs-site.xml
Modified: hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/http/HttpServer.java
URL: http://svn.apache.org/viewvc/hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/http/HttpServer.java?rev=1334216&r1=1334215&r2=1334216&view=diff
==============================================================================
--- hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/http/HttpServer.java (original)
+++ hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/http/HttpServer.java Fri May 4 21:58:44 2012
@@ -52,8 +52,6 @@ import org.apache.hadoop.fs.CommonConfig
import org.apache.hadoop.jmx.JMXJsonServlet;
import org.apache.hadoop.log.LogLevel;
import org.apache.hadoop.metrics.MetricsServlet;
-import org.apache.hadoop.security.Krb5AndCertsSslSocketConnector;
-import org.apache.hadoop.security.Krb5AndCertsSslSocketConnector.MODE;
import org.apache.hadoop.security.UserGroupInformation;
import org.apache.hadoop.security.authorize.AccessControlList;
import org.apache.hadoop.util.ReflectionUtils;
@@ -99,6 +97,7 @@ public class HttpServer implements Filte
// gets stored.
public static final String CONF_CONTEXT_ATTRIBUTE = "hadoop.conf";
static final String ADMINS_ACL = "admins.acl";
+ public static final String SPNEGO_FILTER = "SpnegoFilter";
public static final String BIND_ADDRESS = "bind.address";
@@ -237,11 +236,7 @@ public class HttpServer implements Filte
webServer.addHandler(webAppContext);
addDefaultApps(contexts, appDir, conf);
-
- defineFilter(webAppContext, "krb5Filter",
- Krb5AndCertsSslSocketConnector.Krb5SslFilter.class.getName(),
- null, null);
-
+
addGlobalFilter("safety", QuotingInputFilter.class.getName(), null);
final FilterInitializer[] initializers = getFilterInitializers(conf);
if (initializers != null) {
@@ -424,12 +419,13 @@ public class HttpServer implements Filte
* protect with Kerberos authentication.
* Note: This method is to be used for adding servlets that facilitate
* internal communication and not for user facing functionality. For
- * servlets added using this method, filters (except internal Kerberized
+ + * servlets added using this method, filters (except internal Kerberos
* filters) are not enabled.
*
* @param name The name of the servlet (can be passed as null)
* @param pathSpec The path spec for the servlet
* @param clazz The servlet class
+ * @param requireAuth Require Kerberos authenticate to access servlet
*/
public void addInternalServlet(String name, String pathSpec,
Class<? extends HttpServlet> clazz, boolean requireAuth) {
@@ -440,11 +436,11 @@ public class HttpServer implements Filte
webAppContext.addServlet(holder, pathSpec);
if(requireAuth && UserGroupInformation.isSecurityEnabled()) {
- LOG.info("Adding Kerberos filter to " + name);
+ LOG.info("Adding Kerberos (SPNEGO) filter to " + name);
ServletHandler handler = webAppContext.getServletHandler();
FilterMapping fmap = new FilterMapping();
fmap.setPathSpec(pathSpec);
- fmap.setFilterName("krb5Filter");
+ fmap.setFilterName(SPNEGO_FILTER);
fmap.setDispatches(Handler.ALL);
handler.addFilterMapping(fmap);
}
@@ -584,22 +580,10 @@ public class HttpServer implements Filte
* Configure an ssl listener on the server.
* @param addr address to listen on
* @param sslConf conf to retrieve ssl options
- * @param needClientAuth whether client authentication is required
- */
- public void addSslListener(InetSocketAddress addr, Configuration sslConf,
- boolean needClientAuth) throws IOException {
- addSslListener(addr, sslConf, needClientAuth, false);
- }
-
- /**
- * Configure an ssl listener on the server.
- * @param addr address to listen on
- * @param sslConf conf to retrieve ssl options
* @param needCertsAuth whether x509 certificate authentication is required
- * @param needKrbAuth whether to allow kerberos auth
*/
public void addSslListener(InetSocketAddress addr, Configuration sslConf,
- boolean needCertsAuth, boolean needKrbAuth) throws IOException {
+ boolean needCertsAuth) throws IOException {
if (webServer.isStarted()) {
throw new IOException("Failed to add ssl listener");
}
@@ -612,15 +596,7 @@ public class HttpServer implements Filte
System.setProperty("javax.net.ssl.trustStoreType", sslConf.get(
"ssl.server.truststore.type", "jks"));
}
- Krb5AndCertsSslSocketConnector.MODE mode;
- if(needCertsAuth && needKrbAuth)
- mode = MODE.BOTH;
- else if (!needCertsAuth && needKrbAuth)
- mode = MODE.KRB;
- else // Default to certificates
- mode = MODE.CERTS;
-
- SslSocketConnector sslListener = new Krb5AndCertsSslSocketConnector(mode);
+ SslSocketConnector sslListener = new SslSocketConnector();
sslListener.setHost(addr.getHostName());
sslListener.setPort(addr.getPort());
sslListener.setKeystore(sslConf.get("ssl.server.keystore.location"));
Modified: hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/security/SecurityUtil.java
URL: http://svn.apache.org/viewvc/hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/security/SecurityUtil.java?rev=1334216&r1=1334215&r2=1334216&view=diff
==============================================================================
--- hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/security/SecurityUtil.java (original)
+++ hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/security/SecurityUtil.java Fri May 4 21:58:44 2012
@@ -17,14 +17,11 @@
package org.apache.hadoop.security;
import java.io.IOException;
-import java.lang.reflect.Constructor;
-import java.lang.reflect.Field;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
import java.net.InetAddress;
import java.net.InetSocketAddress;
import java.net.URI;
import java.net.URL;
+import java.net.URLConnection;
import java.net.UnknownHostException;
import java.security.AccessController;
import java.security.PrivilegedAction;
@@ -45,6 +42,8 @@ import org.apache.hadoop.conf.Configurat
import org.apache.hadoop.fs.CommonConfigurationKeys;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.net.NetUtils;
+import org.apache.hadoop.security.authentication.client.AuthenticatedURL;
+import org.apache.hadoop.security.authentication.client.AuthenticationException;
import org.apache.hadoop.security.token.Token;
import org.apache.hadoop.security.token.TokenInfo;
@@ -135,79 +134,6 @@ public class SecurityUtil {
}
/**
- * Explicitly pull the service ticket for the specified host. This solves a
- * problem with Java's Kerberos SSL problem where the client cannot
- * authenticate against a cross-realm service. It is necessary for clients
- * making kerberized https requests to call this method on the target URL
- * to ensure that in a cross-realm environment the remote host will be
- * successfully authenticated.
- *
- * This method is internal to Hadoop and should not be used by other
- * applications. This method should not be considered stable or open:
- * it will be removed when the Java behavior is changed.
- *
- * @param remoteHost Target URL the krb-https client will access
- * @throws IOException if the service ticket cannot be retrieved
- */
- public static void fetchServiceTicket(URL remoteHost) throws IOException {
- if(!UserGroupInformation.isSecurityEnabled())
- return;
-
- String serviceName = "host/" + remoteHost.getHost();
- if (LOG.isDebugEnabled())
- LOG.debug("Fetching service ticket for host at: " + serviceName);
- Object serviceCred = null;
- Method credsToTicketMeth;
- Class<?> krb5utilClass;
- try {
- Class<?> principalClass;
- Class<?> credentialsClass;
-
- if (System.getProperty("java.vendor").contains("IBM")) {
- principalClass = Class.forName("com.ibm.security.krb5.PrincipalName");
-
- credentialsClass = Class.forName("com.ibm.security.krb5.Credentials");
- krb5utilClass = Class.forName("com.ibm.security.jgss.mech.krb5");
- } else {
- principalClass = Class.forName("sun.security.krb5.PrincipalName");
- credentialsClass = Class.forName("sun.security.krb5.Credentials");
- krb5utilClass = Class.forName("sun.security.jgss.krb5.Krb5Util");
- }
- @SuppressWarnings("rawtypes")
- Constructor principalConstructor = principalClass.getConstructor(String.class,
- int.class);
- Field KRB_NT_SRV_HST = principalClass.getDeclaredField("KRB_NT_SRV_HST");
- Method acquireServiceCredsMeth =
- credentialsClass.getDeclaredMethod("acquireServiceCreds",
- String.class, credentialsClass);
- Method ticketToCredsMeth = krb5utilClass.getDeclaredMethod("ticketToCreds",
- KerberosTicket.class);
- credsToTicketMeth = krb5utilClass.getDeclaredMethod("credsToTicket",
- credentialsClass);
-
- Object principal = principalConstructor.newInstance(serviceName,
- KRB_NT_SRV_HST.get(principalClass));
-
- serviceCred = acquireServiceCredsMeth.invoke(credentialsClass,
- principal.toString(),
- ticketToCredsMeth.invoke(krb5utilClass, getTgtFromSubject()));
- } catch (Exception e) {
- throw new IOException("Can't get service ticket for: "
- + serviceName, e);
- }
- if (serviceCred == null) {
- throw new IOException("Can't get service ticket for " + serviceName);
- }
- try {
- Subject.getSubject(AccessController.getContext()).getPrivateCredentials()
- .add(credsToTicketMeth.invoke(krb5utilClass, serviceCred));
- } catch (Exception e) {
- throw new IOException("Can't get service ticket for: "
- + serviceName, e);
- }
- }
-
- /**
* Convert Kerberos principal name pattern to valid Kerberos principal
* names. It replaces hostname pattern with hostname, which should be
* fully-qualified domain name. If hostname is null or "0.0.0.0", it uses
@@ -514,6 +440,30 @@ public class SecurityUtil {
}
/**
+ * Open a (if need be) secure connection to a URL in a secure environment
+ * that is using SPNEGO to authenticate its URLs. All Namenode and Secondary
+ * Namenode URLs that are protected via SPNEGO should be accessed via this
+ * method.
+ *
+ * @param url to authenticate via SPNEGO.
+ * @return A connection that has been authenticated via SPNEGO
+ * @throws IOException If unable to authenticate via SPNEGO
+ */
+ public static URLConnection openSecureHttpConnection(URL url) throws IOException {
+ if(!UserGroupInformation.isSecurityEnabled()) {
+ return url.openConnection();
+ }
+
+ AuthenticatedURL.Token token = new AuthenticatedURL.Token();
+ try {
+ return new AuthenticatedURL().openConnection(url, token);
+ } catch (AuthenticationException e) {
+ throw new IOException("Exception trying to open authenticated connection to "
+ + url, e);
+ }
+ }
+
+ /**
* Resolves a host subject to the security requirements determined by
* hadoop.security.token.service.use_ip.
*
@@ -664,10 +614,4 @@ public class SecurityUtil {
}
}
- public static void initKrb5CipherSuites() {
- if (UserGroupInformation.isSecurityEnabled()) {
- System.setProperty("https.cipherSuites",
- Krb5AndCertsSslSocketConnector.KRB5_CIPHER_SUITES.get(0));
- }
- }
}
Modified: hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/packages/templates/conf/hdfs-site.xml
URL: http://svn.apache.org/viewvc/hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/packages/templates/conf/hdfs-site.xml?rev=1334216&r1=1334215&r2=1334216&view=diff
==============================================================================
--- hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/packages/templates/conf/hdfs-site.xml (original)
+++ hadoop/common/trunk/hadoop-common-project/hadoop-common/src/main/packages/templates/conf/hdfs-site.xml Fri May 4 21:58:44 2012
@@ -129,13 +129,6 @@
</property>
<property>
- <name>dfs.secondary.https.port</name>
- <value>50490</value>
- <description>The https port where secondary-namenode binds</description>
-
- </property>
-
- <property>
<name>dfs.datanode.kerberos.principal</name>
<value>dn/_HOST@${local.realm}</value>
<description>