Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

8279064: New options for ktab to provide non-default salt #6991

Closed
wants to merge 2 commits into from
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2000, 2021, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2000, 2022, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -376,12 +376,33 @@ public void addEntry(PrincipalName service, char[] psswd,
addEntry(service, service.getSalt(), psswd, kvno, append);
}

// Called by KDC test
/**
* Adds a new entry in the key table.
* @param service the service which will have a new entry in the key table.
* @param salt specified non default salt, cannot be null
* @param psswd the password which generates the key.
* @param kvno the kvno to use, -1 means automatic increasing
* @param append false if entries with old kvno would be removed.
* Note: if kvno is not -1, entries with the same kvno are always removed
*/
public void addEntry(PrincipalName service, String salt, char[] psswd,
int kvno, boolean append) throws KrbException {

EncryptionKey[] encKeys = EncryptionKey.acquireSecretKeys(
psswd, salt);
psswd, salt);
addEntry(service, encKeys, kvno, append);
}

/**
* Adds a new entry in the key table.
* @param service the service which will have a new entry in the key table.
* @param encKeys the keys to be added
* @param kvno the kvno to use, -1 means automatic increasing
* @param append false if entries with old kvno would be removed.
* Note: if kvno is not -1, entries with the same kvno are always removed
*/
public void addEntry(PrincipalName service, EncryptionKey[] encKeys,
int kvno, boolean append) throws KrbException {

// There should be only one maximum KVNO value for all etypes, so that
// all added keys can have the same KVNO.
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2003, 2018, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2003, 2022, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -35,7 +35,6 @@
import java.io.IOException;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.File;
import java.text.DateFormat;
import java.util.Arrays;
import java.util.Date;
@@ -61,10 +60,12 @@ public class Ktab {
int etype = -1;
char[] password = null;

boolean forced = false; // true if delete without prompt. Default false
boolean fopt = false; // true if delete without prompt or
// add by contacting KDC. Default false
boolean append = false; // true if new keys are appended. Default false
int vDel = -1; // kvno to delete, -1 all, -2 old. Default -1
int vAdd = -1; // kvno to add. Default -1, means auto incremented
String salt = null; // salt to use. Default null, means default salt

/**
* The main program that can be invoked at command line.
@@ -186,6 +187,12 @@ void processArgs(String[] args) {
error(args[i] + " is not valid after -" + action);
}
break;
case "-s": // salt for -a
if (++i >= args.length || args[i].startsWith("-")) {
error("A salt string must be specified after -s");
}
salt = args[i];
break;
case "-n": // kvno for -a
if (++i >= args.length || args[i].startsWith("-")) {
error("A KVNO must be specified after -n");
@@ -213,8 +220,8 @@ void processArgs(String[] args) {
case "-t": // list timestamps
showTime = true;
break;
case "-f": // force delete, no prompt
forced = true;
case "-f": // force delete or get salt from KDC
fopt = true;
break;
case "-append": // -a, new keys append to file
append = true;
@@ -258,6 +265,10 @@ void processArgs(String[] args) {
* a new key table.
*/
void addEntry() {
if (salt != null && fopt) {
System.err.println("-s and -f cannot coexist when adding a keytab entry.");
System.exit(-1);
}
PrincipalName pname = null;
try {
pname = new PrincipalName(principal);
@@ -283,7 +294,15 @@ void addEntry() {
}
try {
// admin.addEntry(pname, password);
table.addEntry(pname, password, vAdd, append);
if (fopt) {
KrbAsReqBuilder builder = new KrbAsReqBuilder(pname, password);
builder.action();
table.addEntry(pname, builder.getKeys(true), vAdd, append);
} else if (salt != null) {
table.addEntry(pname, salt, password, vAdd, append);
} else {
table.addEntry(pname, password, vAdd, append);
}
Arrays.fill(password, '0'); // clear password
// admin.save();
table.save();
@@ -367,7 +386,7 @@ void deleteEntry() {
PrincipalName pname = null;
try {
pname = new PrincipalName(principal);
if (!forced) {
if (!fopt) {
String answer;
BufferedReader cis =
new BufferedReader(new InputStreamReader(System.in));
@@ -424,6 +443,7 @@ void error(String... errors) {
printHelp();
System.exit(-1);
}

/**
* Prints out the help information.
*/
@@ -434,11 +454,13 @@ void printHelp() {
System.out.println();
System.out.println("-l [-e] [-t]\n"
+ " list the keytab name and entries. -e with etype, -t with timestamp.");
System.out.println("-a <principal name> [<password>] [-n <kvno>] [-append]\n"
System.out.println("-a <principal name> [<password>] [-n <kvno>] [-f | -s <salt>] [-append]\n"
+ " add new key entries to the keytab for the given principal name with\n"
+ " optional <password>. If a <kvno> is specified, new keys' Key Version\n"
+ " Numbers equal to the value, otherwise, automatically incrementing\n"
+ " the Key Version Numbers. If -append is specified, new keys are\n"
+ " the Key Version Numbers. If <salt> is specified, it will be used\n"
+ " instead of the default salt. If -f is specified, the KDC will be\n"
+ " contacted to fetch the salt. If -append is specified, new keys are\n"
+ " appended to the keytab, otherwise, old keys for the\n"
+ " same principal are removed.");
System.out.println("-d <principal name> [-f] [-e <etype>] [<kvno> | all | old]\n"
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2008, 2021, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2008, 2022, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -207,13 +207,26 @@ public static Context fromUserKtab(
*/
public static Context fromUserKtab(Subject s,
String user, String ktab, boolean storeKey) throws Exception {
return fromUserKtab(s, user, ktab, false, storeKey);
}

/**
* Logins with username/keytab as a client.
*/
public static Context fromUserKtabAsClient(
String user, String ktab, boolean storeKey) throws Exception {
return fromUserKtab(new Subject(), user, ktab, true, storeKey);
}

private static Context fromUserKtab(Subject s,
String user, String ktab, boolean isInitiator, boolean storeKey) throws Exception {
Context out = new Context();
out.name = user;
out.s = s;
Krb5LoginModule krb5 = new Krb5LoginModule();
Map<String, String> map = new HashMap<>();

map.put("isInitiator", "false");
map.put("isInitiator", Boolean.toString(isInitiator));
map.put("doNotPrompt", "true");
map.put("useTicketCache", "false");
map.put("useKeyTab", "true");
@@ -0,0 +1,78 @@
/*
* Copyright (c) 2022, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/

/*
* @test
* @bug 8279064
* @summary New options for ktab to provide non-default salt
* @requires os.family == "windows"
* @library /test/lib
* @library /sun/security/krb5/auto
* @compile -XDignore.symbol.file KtabSalt.java
* @run main jdk.test.lib.FileInstaller ../TestHosts TestHosts
* @run main/othervm -Djdk.net.hosts.file=TestHosts KtabSalt
*/

import jdk.test.lib.SecurityTools;
import jdk.test.lib.Utils;
import jdk.test.lib.process.OutputAnalyzer;

import javax.security.auth.login.LoginException;

public class KtabSalt {

public static void main(String[] args) throws Exception {

OneKDC kdc = new OneKDC(null).writeJAASConf();
kdc.addPrincipal("u1", "password".toCharArray(),
"this_is_my_salt", null);

// Using password works
Context.fromUserPass("u1", "password".toCharArray(), true);

// Using KDC's keytab works
kdc.writeKtab("ktab0");
Context.fromUserKtabAsClient("u1", "ktab0", true);

// Self-created keytab with default salt does not work
ktab("-a u1 password -k ktab1");
Utils.runAndCheckException(
() -> Context.fromUserKtabAsClient("u1", "ktab1", true),
LoginException.class);

// Self-creating keytab with specified salt works
ktab("-a u1 password -s this_is_my_salt -k ktab2");
Context.fromUserKtabAsClient("u1", "ktab2", true);

// Self-creating keytab with salt from KDC works
ktab("-a u1 password -f -k ktab3");
Context.fromUserKtabAsClient("u1", "ktab3", true);
}

static OutputAnalyzer ktab(String cmdLine) throws Exception {
String fullCmdLine = String.format(
"-J-Djava.security.krb5.conf=%s -J-Djdk.net.hosts.file=TestHosts %s",
OneKDC.KRB5_CONF, cmdLine);
return SecurityTools.ktab(fullCmdLine).shouldHaveExitValue(0);
}
}
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2010, 2021, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2010, 2022, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -69,31 +69,31 @@ public static void main(String[] args) throws Exception {
check(3,17,3,18,3,19,4,17,4,18,4,19,5,17,5,18,5,19);
ktab("-a me mine -n 6 -append");
check(3,17,3,18,3,19,4,17,4,18,4,19,5,17,5,18,5,19,6,17,6,18,6,19);
ktab("-d me 3");
ktab("-d me -f 3");
check(4,17,4,18,4,19,5,17,5,18,5,19,6,17,6,18,6,19);
ktab("-d me -e 17 6");
ktab("-d me -f -e 17 6");
check(4,17,4,18,4,19,5,17,5,18,5,19,6,18,6,19);
ktab("-d me -e 19 6");
ktab("-d me -f -e 19 6");
check(4,17,4,18,4,19,5,17,5,18,5,19,6,18);
ktab("-d me -e 17 5");
ktab("-d me -f -e 17 5");
check(4,17,4,18,4,19,5,18,5,19,6,18);
ktab("-d me old");
ktab("-d me -f old");
check(4,17,5,19,6,18);
try {
ktab("-d me old");
ktab("-d me -f old");
throw new Exception("Should fail");
} catch (Exception e) {
// no-op
}
check(4,17,5,19,6,18);
ktab("-d me");
ktab("-d me -f");
check();
}

static void ktab(String s) throws Exception {
File conf = new File(System.getProperty("test.src"), "onlythree.conf");
SecurityTools.ktab("-J-Djava.security.krb5.conf=" + conf
+ " -k " + KEYTAB + " -f " + s).shouldHaveExitValue(0);
+ " -k " + KEYTAB + " " + s).shouldHaveExitValue(0);
}

/**