Path: blob/master/src/java.security.jgss/share/classes/sun/security/krb5/KrbAsRep.java
41159 views
/*1* Copyright (c) 2000, 2019, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation. Oracle designates this7* particular file as subject to the "Classpath" exception as provided8* by Oracle in the LICENSE file that accompanied this code.9*10* This code is distributed in the hope that it will be useful, but WITHOUT11* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or12* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License13* version 2 for more details (a copy is included in the LICENSE file that14* accompanied this code).15*16* You should have received a copy of the GNU General Public License version17* 2 along with this work; if not, write to the Free Software Foundation,18* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.19*20* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA21* or visit www.oracle.com if you need additional information or have any22* questions.23*/2425/*26*27* (C) Copyright IBM Corp. 1999 All Rights Reserved.28* Copyright 1997 The Open Group Research Institute. All rights reserved.29*/3031package sun.security.krb5;3233import sun.security.krb5.internal.*;34import sun.security.krb5.internal.crypto.KeyUsage;35import sun.security.krb5.internal.crypto.EType;36import sun.security.util.*;37import java.io.IOException;38import java.util.Objects;39import javax.security.auth.kerberos.KeyTab;40import sun.security.jgss.krb5.Krb5Util;4142/**43* This class encapsulates a AS-REP message that the KDC sends to the44* client.45*/46class KrbAsRep extends KrbKdcRep {4748private ASRep rep; // The AS-REP message49private Credentials creds; // The Credentials provide by the AS-REP50// message, created by initiator after calling51// the decrypt() method5253private boolean DEBUG = Krb5.DEBUG;5455KrbAsRep(byte[] ibuf) throws56KrbException, Asn1Exception, IOException {57DerValue encoding = new DerValue(ibuf);58try {59rep = new ASRep(encoding);60} catch (Asn1Exception e) {61rep = null;62KRBError err = new KRBError(encoding);63String errStr = err.getErrorString();64String eText = null; // pick up text sent by the server (if any)6566if (errStr != null && errStr.length() > 0) {67if (errStr.charAt(errStr.length() - 1) == 0)68eText = errStr.substring(0, errStr.length() - 1);69else70eText = errStr;71}72KrbException ke;73if (eText == null) {74// no text sent from server75ke = new KrbException(err);76} else {77if (DEBUG) {78System.out.println("KRBError received: " + eText);79}80// override default text with server text81ke = new KrbException(err, eText);82}83ke.initCause(e);84throw ke;85}86}8788// KrbAsReqBuilder need to read back the PA for key generation89PAData[] getPA() {90return rep.pAData;91}9293/**94* Called by KrbAsReqBuilder to resolve a AS-REP message using a keytab.95* @param ktab the keytab, not null96* @param asReq the original AS-REQ sent, used to validate AS-REP97* @param cname the user principal name, used to locate keys in ktab98*/99void decryptUsingKeyTab(KeyTab ktab, KrbAsReq asReq, PrincipalName cname)100throws KrbException, Asn1Exception, IOException {101EncryptionKey dkey = null;102int encPartKeyType = rep.encPart.getEType();103Integer encPartKvno = rep.encPart.kvno;104try {105dkey = EncryptionKey.findKey(encPartKeyType, encPartKvno,106Krb5Util.keysFromJavaxKeyTab(ktab, cname));107} catch (KrbException ke) {108if (ke.returnCode() == Krb5.KRB_AP_ERR_BADKEYVER) {109// Fallback to no kvno. In some cases, keytab is generated110// not by sysadmin but Java's ktab command111dkey = EncryptionKey.findKey(encPartKeyType,112Krb5Util.keysFromJavaxKeyTab(ktab, cname));113}114}115if (dkey == null) {116throw new KrbException(Krb5.API_INVALID_ARG,117"Cannot find key for type/kvno to decrypt AS REP - " +118EType.toString(encPartKeyType) + "/" + encPartKvno);119}120decrypt(dkey, asReq, cname);121}122123/**124* Called by KrbAsReqBuilder to resolve a AS-REP message using a password.125* @param password user provided password. not null126* @param asReq the original AS-REQ sent, used to validate AS-REP127* @param cname the user principal name, used to provide salt128*/129void decryptUsingPassword(char[] password,130KrbAsReq asReq, PrincipalName cname)131throws KrbException, Asn1Exception, IOException {132int encPartKeyType = rep.encPart.getEType();133EncryptionKey dkey = EncryptionKey.acquireSecretKey(134cname,135password,136encPartKeyType,137PAData.getSaltAndParams(encPartKeyType, rep.pAData));138decrypt(dkey, asReq, cname);139}140141/**142* Decrypts encrypted content inside AS-REP. Called by initiator.143* @param dkey the decryption key to use144* @param asReq the original AS-REQ sent, used to validate AS-REP145*/146private void decrypt(EncryptionKey dkey, KrbAsReq asReq,147PrincipalName cname)148throws KrbException, Asn1Exception, IOException {149byte[] enc_as_rep_bytes = rep.encPart.decrypt(dkey,150KeyUsage.KU_ENC_AS_REP_PART);151byte[] enc_as_rep_part = rep.encPart.reset(enc_as_rep_bytes);152153DerValue encoding = new DerValue(enc_as_rep_part);154EncASRepPart enc_part = new EncASRepPart(encoding);155rep.encKDCRepPart = enc_part;156157ASReq req = asReq.getMessage();158check(true, req, rep, dkey);159160PrincipalName clientAlias = cname;161if (clientAlias.equals(rep.cname))162clientAlias = null;163164creds = new Credentials(165rep.ticket,166rep.cname,167clientAlias,168enc_part.sname,169null, // No server alias expected in a TGT170enc_part.key,171enc_part.flags,172enc_part.authtime,173enc_part.starttime,174enc_part.endtime,175enc_part.renewTill,176enc_part.caddr);177if (DEBUG) {178System.out.println(">>> KrbAsRep cons in KrbAsReq.getReply " +179req.reqBody.cname.getNameString());180}181}182183Credentials getCreds() {184return Objects.requireNonNull(creds, "Creds not available yet.");185}186187sun.security.krb5.internal.ccache.Credentials getCCreds() {188return new sun.security.krb5.internal.ccache.Credentials(rep);189}190}191192193