| diff --git a/hadoop-common-project/hadoop-auth/pom.xml b/hadoop-common-project/hadoop-auth/pom.xml |
| index aa3c2c7..e4f1fd2 100644 |
| --- a/hadoop-common-project/hadoop-auth/pom.xml |
| +++ b/hadoop-common-project/hadoop-auth/pom.xml |
| @@ -143,6 +143,11 @@ |
| <artifactId>curator-test</artifactId> |
| <scope>test</scope> |
| </dependency> |
| + <dependency> |
| + <groupId>org.apache.kerby</groupId> |
| + <artifactId>has-client</artifactId> |
| + <version>1.0.0-SNAPSHOT</version> |
| + </dependency> |
| </dependencies> |
| |
| <build> |
| diff --git a/hadoop-common-project/hadoop-auth/src/main/java/org/apache/hadoop/security/authentication/util/KerberosUtil.java b/hadoop-common-project/hadoop-auth/src/main/java/org/apache/hadoop/security/authentication/util/KerberosUtil.java |
| index f7f5f63..80b7aca 100644 |
| --- a/hadoop-common-project/hadoop-auth/src/main/java/org/apache/hadoop/security/authentication/util/KerberosUtil.java |
| +++ b/hadoop-common-project/hadoop-auth/src/main/java/org/apache/hadoop/security/authentication/util/KerberosUtil.java |
| @@ -44,7 +44,8 @@ |
| public static String getKrb5LoginModuleName() { |
| return System.getProperty("java.vendor").contains("IBM") |
| ? "com.ibm.security.auth.module.Krb5LoginModule" |
| - : "com.sun.security.auth.module.Krb5LoginModule"; |
| +// : "com.sun.security.auth.module.Krb5LoginModule"; |
| + :"org.apache.kerby.has.client.HasLoginModule"; |
| } |
| |
| public static Oid getOidInstance(String oidName) |
| diff --git a/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/security/UserGroupInformation.java b/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/security/UserGroupInformation.java |
| index 65e4166..f5224bb 100644 |
| --- a/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/security/UserGroupInformation.java |
| +++ b/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/security/UserGroupInformation.java |
| @@ -89,6 +89,8 @@ |
| private static boolean shouldRenewImmediatelyForTests = false; |
| static final String HADOOP_USER_NAME = "HADOOP_USER_NAME"; |
| static final String HADOOP_PROXY_USER = "HADOOP_PROXY_USER"; |
| + public static final String HADOOP_SECURITY_AUTHENTICATION_USE_HAS |
| + = "hadoop.security.authentication.use.has"; |
| |
| /** |
| * For the purposes of unit tests, we want to test login |
| @@ -460,6 +462,9 @@ public String toString() { |
| "hadoop-user-kerberos"; |
| private static final String KEYTAB_KERBEROS_CONFIG_NAME = |
| "hadoop-keytab-kerberos"; |
| + private static final String HAS_KERBEROS_CONFIG_NAME = |
| + "hadoop-has-kerberos"; |
| + |
| |
| private static final Map<String, String> BASIC_JAAS_OPTIONS = |
| new HashMap<String,String>(); |
| @@ -516,6 +521,29 @@ public String toString() { |
| KEYTAB_KERBEROS_OPTIONS.put("refreshKrb5Config", "true"); |
| KEYTAB_KERBEROS_OPTIONS.putAll(BASIC_JAAS_OPTIONS); |
| } |
| + |
| + private static final Map<String, String> HAS_KERBEROS_OPTIONS = |
| + new HashMap<String, String>(); |
| + |
| + static { |
| + if (IBM_JAVA) { |
| + HAS_KERBEROS_OPTIONS.put("useDefaultCcache", "true"); |
| + } else { |
| + HAS_KERBEROS_OPTIONS.put("doNotPrompt", "true"); |
| + HAS_KERBEROS_OPTIONS.put("useTgtTicket", "true"); |
| + HAS_KERBEROS_OPTIONS.put("hadoopSecurityHas", conf.get("hadoop.security.has")); |
| + } |
| + HAS_KERBEROS_OPTIONS.putAll(BASIC_JAAS_OPTIONS); |
| + } |
| + |
| + private static final AppConfigurationEntry HAS_KERBEROS_LOGIN = |
| + new AppConfigurationEntry(KerberosUtil.getKrb5LoginModuleName(), |
| + LoginModuleControlFlag.OPTIONAL, |
| + HAS_KERBEROS_OPTIONS); |
| + private static final AppConfigurationEntry[] HAS_KERBEROS_CONF = |
| + new AppConfigurationEntry[]{OS_SPECIFIC_LOGIN, HAS_KERBEROS_LOGIN, |
| + HADOOP_LOGIN}; |
| + |
| private static final AppConfigurationEntry KEYTAB_KERBEROS_LOGIN = |
| new AppConfigurationEntry(KerberosUtil.getKrb5LoginModuleName(), |
| LoginModuleControlFlag.REQUIRED, |
| @@ -546,6 +574,8 @@ public String toString() { |
| } |
| KEYTAB_KERBEROS_OPTIONS.put("principal", keytabPrincipal); |
| return KEYTAB_KERBEROS_CONF; |
| + } else if(HAS_KERBEROS_CONFIG_NAME.equals(appName)) { |
| + return HAS_KERBEROS_CONF; |
| } |
| return null; |
| } |
| @@ -792,9 +822,16 @@ static void loginUserFromSubject(Subject subject) throws IOException { |
| if (subject == null) { |
| subject = new Subject(); |
| } |
| - LoginContext login = |
| - newLoginContext(authenticationMethod.getLoginAppName(), |
| - subject, new HadoopConfiguration()); |
| + LoginContext login = null; |
| + if (authenticationMethod.equals(AuthenticationMethod.KERBEROS) |
| + && conf.getBoolean(HADOOP_SECURITY_AUTHENTICATION_USE_HAS, false)) { |
| + login = newLoginContext(HadoopConfiguration.HAS_KERBEROS_CONFIG_NAME, |
| + subject, new HadoopConfiguration()); |
| + } else { |
| + login = newLoginContext(authenticationMethod.getLoginAppName(), |
| + subject, new HadoopConfiguration()); |
| + } |
| + |
| login.login(); |
| UserGroupInformation realUser = new UserGroupInformation(subject); |
| realUser.setLogin(login); |
| @@ -925,6 +962,39 @@ public void run() { |
| } |
| } |
| } |
| + |
| + /** |
| + * Log a user in from a tgt ticket. |
| + * @throws IOException |
| + */ |
| + @InterfaceAudience.Public |
| + @InterfaceStability.Evolving |
| + public synchronized |
| + static void loginUserFromHas() throws IOException { |
| + if (!isSecurityEnabled()) |
| + return; |
| + |
| + Subject subject = new Subject(); |
| + LoginContext login; |
| + long start = 0; |
| + try { |
| + login = newLoginContext(HadoopConfiguration.HAS_KERBEROS_CONFIG_NAME, |
| + subject, new HadoopConfiguration()); |
| + start = Time.now(); |
| + login.login(); |
| + metrics.loginSuccess.add(Time.now() - start); |
| + loginUser = new UserGroupInformation(subject); |
| + loginUser.setLogin(login); |
| + loginUser.setAuthenticationMethod(AuthenticationMethod.KERBEROS); |
| + } catch (LoginException le) { |
| + if (start > 0) { |
| + metrics.loginFailure.add(Time.now() - start); |
| + } |
| + throw new IOException("Login failure for " + le, le); |
| + } |
| + LOG.info("Login successful for user " + loginUser.getUserName()); |
| + } |
| + |
| /** |
| * Log a user in from a keytab file. Loads a user identity from a keytab |
| * file and logs them in. They become the currently logged-in user. |