test/jdk/sun/security/krb5/auto/KDC.java
branchdatagramsocketimpl-branch
changeset 58678 9cf78a70fa4f
parent 53273 bbc79e0ec9ee
child 58679 9c3209ff7550
equal deleted inserted replaced
58677:13588c901957 58678:9cf78a70fa4f
   163     // different s2kparams for different etypes, pretend they are the same
   163     // different s2kparams for different etypes, pretend they are the same
   164     // at the moment.
   164     // at the moment.
   165     private TreeMap<String,byte[]> s2kparamses = new TreeMap<>
   165     private TreeMap<String,byte[]> s2kparamses = new TreeMap<>
   166             (String.CASE_INSENSITIVE_ORDER);
   166             (String.CASE_INSENSITIVE_ORDER);
   167 
   167 
       
   168     // Alias for referrals.
       
   169     private TreeMap<String,KDC> aliasReferrals = new TreeMap<>
       
   170             (String.CASE_INSENSITIVE_ORDER);
       
   171 
       
   172     // Alias for local resolution.
       
   173     private TreeMap<String,PrincipalName> alias2Principals = new TreeMap<>
       
   174             (String.CASE_INSENSITIVE_ORDER);
       
   175 
   168     // Realm name
   176     // Realm name
   169     private String realm;
   177     private String realm;
   170     // KDC
   178     // KDC
   171     private String kdc;
   179     private String kdc;
   172     // Service port number
   180     // Service port number
   551      */
   559      */
   552     public int getPort() {
   560     public int getPort() {
   553         return port;
   561         return port;
   554     }
   562     }
   555 
   563 
       
   564     /**
       
   565      * Register an alias name to be referred to a different KDC for
       
   566      * resolution, according to RFC 6806.
       
   567      * @param alias Alias name (i.e. user@REALM.COM).
       
   568      * @param referredKDC KDC to which the alias is referred for resolution.
       
   569      */
       
   570     public void registerAlias(String alias, KDC referredKDC) {
       
   571         aliasReferrals.remove(alias);
       
   572         aliasReferrals.put(alias, referredKDC);
       
   573     }
       
   574 
       
   575     /**
       
   576      * Register an alias to be resolved to a Principal Name locally,
       
   577      * according to RFC 6806.
       
   578      * @param alias Alias name (i.e. user@REALM.COM).
       
   579      * @param user Principal Name to which the alias is resolved.
       
   580      */
       
   581     public void registerAlias(String alias, String user)
       
   582             throws RealmException {
       
   583         alias2Principals.remove(alias);
       
   584         alias2Principals.put(alias, new PrincipalName(user));
       
   585     }
       
   586 
   556     // Private helper methods
   587     // Private helper methods
   557 
   588 
   558     /**
   589     /**
   559      * Private constructor, cannot be called outside.
   590      * Private constructor, cannot be called outside.
   560      * @param realm
   591      * @param realm
   775             Ticket tkt = null;
   806             Ticket tkt = null;
   776             EncTicketPart etp = null;
   807             EncTicketPart etp = null;
   777 
   808 
   778             PrincipalName cname = null;
   809             PrincipalName cname = null;
   779             boolean allowForwardable = true;
   810             boolean allowForwardable = true;
       
   811             boolean isReferral = false;
       
   812             if (body.kdcOptions.get(KDCOptions.CANONICALIZE)) {
       
   813                 System.out.println(realm + "> verifying referral for " +
       
   814                         body.sname.getNameString());
       
   815                 KDC referral = aliasReferrals.get(body.sname.getNameString());
       
   816                 if (referral != null) {
       
   817                     service = new PrincipalName(
       
   818                             PrincipalName.TGS_DEFAULT_SRV_NAME +
       
   819                             PrincipalName.NAME_COMPONENT_SEPARATOR_STR +
       
   820                             referral.getRealm(), PrincipalName.KRB_NT_SRV_INST,
       
   821                             this.getRealm());
       
   822                     System.out.println(realm + "> referral to " +
       
   823                             referral.getRealm());
       
   824                     isReferral = true;
       
   825                 }
       
   826             }
   780 
   827 
   781             if (pas == null || pas.length == 0) {
   828             if (pas == null || pas.length == 0) {
   782                 throw new KrbException(Krb5.KDC_ERR_PADATA_TYPE_NOSUPP);
   829                 throw new KrbException(Krb5.KDC_ERR_PADATA_TYPE_NOSUPP);
   783             } else {
   830             } else {
   784                 PrincipalName forUserCName = null;
   831                 PrincipalName forUserCName = null;
   874                 bFlags[Krb5.TKT_OPTS_POSTDATED] = true;
   921                 bFlags[Krb5.TKT_OPTS_POSTDATED] = true;
   875             }
   922             }
   876             if (body.kdcOptions.get(KDCOptions.ALLOW_POSTDATE)) {
   923             if (body.kdcOptions.get(KDCOptions.ALLOW_POSTDATE)) {
   877                 bFlags[Krb5.TKT_OPTS_MAY_POSTDATE] = true;
   924                 bFlags[Krb5.TKT_OPTS_MAY_POSTDATE] = true;
   878             }
   925             }
   879             if (body.kdcOptions.get(KDCOptions.CNAME_IN_ADDL_TKT)) {
   926             if (body.kdcOptions.get(KDCOptions.CNAME_IN_ADDL_TKT) &&
       
   927                     !isReferral) {
   880                 if (!options.containsKey(Option.ALLOW_S4U2PROXY)) {
   928                 if (!options.containsKey(Option.ALLOW_S4U2PROXY)) {
   881                     // Don't understand CNAME_IN_ADDL_TKT
   929                     // Don't understand CNAME_IN_ADDL_TKT
   882                     throw new KrbException(Krb5.KDC_ERR_BADOPTION);
   930                     throw new KrbException(Krb5.KDC_ERR_BADOPTION);
   883                 } else {
   931                 } else {
   884                     Map<String,List<String>> map = (Map<String,List<String>>)
   932                     Map<String,List<String>> map = (Map<String,List<String>>)
   962                     tFlags,
  1010                     tFlags,
   963                     timeAfter(0),
  1011                     timeAfter(0),
   964                     from,
  1012                     from,
   965                     till, renewTill,
  1013                     till, renewTill,
   966                     service,
  1014                     service,
   967                     body.addresses
  1015                     body.addresses,
       
  1016                     null
   968                     );
  1017                     );
   969             EncryptedData edata = new EncryptedData(ckey, enc_part.asn1Encode(),
  1018             EncryptedData edata = new EncryptedData(ckey, enc_part.asn1Encode(),
   970                     KeyUsage.KU_ENC_TGS_REP_PART_SESSKEY);
  1019                     KeyUsage.KU_ENC_TGS_REP_PART_SESSKEY);
   971             TGSRep tgsRep = new TGSRep(null,
  1020             TGSRep tgsRep = new TGSRep(null,
   972                     cname,
  1021                     cname,
  1006      * @return the response
  1055      * @return the response
  1007      * @throws java.lang.Exception for various errors
  1056      * @throws java.lang.Exception for various errors
  1008      */
  1057      */
  1009     protected byte[] processAsReq(byte[] in) throws Exception {
  1058     protected byte[] processAsReq(byte[] in) throws Exception {
  1010         ASReq asReq = new ASReq(in);
  1059         ASReq asReq = new ASReq(in);
       
  1060         byte[] asReqbytes = asReq.asn1Encode();
  1011         int[] eTypes = null;
  1061         int[] eTypes = null;
  1012         List<PAData> outPAs = new ArrayList<>();
  1062         List<PAData> outPAs = new ArrayList<>();
  1013 
  1063 
  1014         PrincipalName service = asReq.reqBody.sname;
  1064         PrincipalName service = asReq.reqBody.sname;
  1015         if (options.containsKey(KDC.Option.RESP_NT)) {
  1065         if (options.containsKey(KDC.Option.RESP_NT)) {
  1027             eTypes = filterSupported(KDCReqBodyDotEType(body));
  1077             eTypes = filterSupported(KDCReqBodyDotEType(body));
  1028             if (eTypes.length == 0) {
  1078             if (eTypes.length == 0) {
  1029                 throw new KrbException(Krb5.KDC_ERR_ETYPE_NOSUPP);
  1079                 throw new KrbException(Krb5.KDC_ERR_ETYPE_NOSUPP);
  1030             }
  1080             }
  1031             int eType = eTypes[0];
  1081             int eType = eTypes[0];
       
  1082 
       
  1083             if (body.kdcOptions.get(KDCOptions.CANONICALIZE)) {
       
  1084                 PrincipalName principal = alias2Principals.get(
       
  1085                         body.cname.getNameString());
       
  1086                 if (principal != null) {
       
  1087                     body.cname = principal;
       
  1088                 } else {
       
  1089                     KDC referral = aliasReferrals.get(body.cname.getNameString());
       
  1090                     if (referral != null) {
       
  1091                         body.cname = new PrincipalName(
       
  1092                                 PrincipalName.TGS_DEFAULT_SRV_NAME,
       
  1093                                 PrincipalName.KRB_NT_SRV_INST,
       
  1094                                 referral.getRealm());
       
  1095                         throw new KrbException(Krb5.KRB_ERR_WRONG_REALM);
       
  1096                     }
       
  1097                 }
       
  1098             }
  1032 
  1099 
  1033             EncryptionKey ckey = keyForUser(body.cname, eType, false);
  1100             EncryptionKey ckey = keyForUser(body.cname, eType, false);
  1034             EncryptionKey skey = keyForUser(service, eType, true);
  1101             EncryptionKey skey = keyForUser(service, eType, true);
  1035 
  1102 
  1036             if (options.containsKey(KDC.Option.ONLY_RC4_TGT)) {
  1103             if (options.containsKey(KDC.Option.ONLY_RC4_TGT)) {
  1209                 eid.putSequence(pas);
  1276                 eid.putSequence(pas);
  1210                 outPAs.add(new PAData(Krb5.PA_ETYPE_INFO, eid.toByteArray()));
  1277                 outPAs.add(new PAData(Krb5.PA_ETYPE_INFO, eid.toByteArray()));
  1211             }
  1278             }
  1212 
  1279 
  1213             PAData[] inPAs = KDCReqDotPAData(asReq);
  1280             PAData[] inPAs = KDCReqDotPAData(asReq);
  1214             if (inPAs == null || inPAs.length == 0) {
  1281             List<PAData> enc_outPAs = new ArrayList<>();
       
  1282 
       
  1283             byte[] paEncTimestamp = null;
       
  1284             if (inPAs != null) {
       
  1285                 for (PAData inPA : inPAs) {
       
  1286                     if (inPA.getType() == Krb5.PA_ENC_TIMESTAMP) {
       
  1287                         paEncTimestamp = inPA.getValue();
       
  1288                     }
       
  1289                 }
       
  1290             }
       
  1291 
       
  1292             if (paEncTimestamp == null) {
  1215                 Object preauth = options.get(Option.PREAUTH_REQUIRED);
  1293                 Object preauth = options.get(Option.PREAUTH_REQUIRED);
  1216                 if (preauth == null || preauth.equals(Boolean.TRUE)) {
  1294                 if (preauth == null || preauth.equals(Boolean.TRUE)) {
  1217                     throw new KrbException(Krb5.KDC_ERR_PREAUTH_REQUIRED);
  1295                     throw new KrbException(Krb5.KDC_ERR_PREAUTH_REQUIRED);
  1218                 }
  1296                 }
  1219             } else {
  1297             } else {
       
  1298                 EncryptionKey pakey = null;
  1220                 try {
  1299                 try {
  1221                     EncryptedData data = newEncryptedData(
  1300                     EncryptedData data = newEncryptedData(
  1222                             new DerValue(inPAs[0].getValue()));
  1301                             new DerValue(paEncTimestamp));
  1223                     EncryptionKey pakey
  1302                     pakey = keyForUser(body.cname, data.getEType(), false);
  1224                             = keyForUser(body.cname, data.getEType(), false);
       
  1225                     data.decrypt(pakey, KeyUsage.KU_PA_ENC_TS);
  1303                     data.decrypt(pakey, KeyUsage.KU_PA_ENC_TS);
  1226                 } catch (Exception e) {
  1304                 } catch (Exception e) {
  1227                     KrbException ke = new KrbException(Krb5.KDC_ERR_PREAUTH_FAILED);
  1305                     KrbException ke = new KrbException(Krb5.KDC_ERR_PREAUTH_FAILED);
  1228                     ke.initCause(e);
  1306                     ke.initCause(e);
  1229                     throw ke;
  1307                     throw ke;
  1230                 }
  1308                 }
  1231                 bFlags[Krb5.TKT_OPTS_PRE_AUTHENT] = true;
  1309                 bFlags[Krb5.TKT_OPTS_PRE_AUTHENT] = true;
       
  1310                 for (PAData pa : inPAs) {
       
  1311                     if (pa.getType() == Krb5.PA_REQ_ENC_PA_REP) {
       
  1312                         Checksum ckSum = new Checksum(
       
  1313                                 Checksum.CKSUMTYPE_HMAC_SHA1_96_AES128,
       
  1314                                 asReqbytes, ckey, KeyUsage.KU_AS_REQ);
       
  1315                         enc_outPAs.add(new PAData(Krb5.PA_REQ_ENC_PA_REP,
       
  1316                                 ckSum.asn1Encode()));
       
  1317                         bFlags[Krb5.TKT_OPTS_ENC_PA_REP] = true;
       
  1318                         break;
       
  1319                     }
       
  1320                 }
  1232             }
  1321             }
  1233 
  1322 
  1234             TicketFlags tFlags = new TicketFlags(bFlags);
  1323             TicketFlags tFlags = new TicketFlags(bFlags);
  1235             EncTicketPart enc = new EncTicketPart(
  1324             EncTicketPart enc = new EncTicketPart(
  1236                     tFlags,
  1325                     tFlags,
  1257                     tFlags,
  1346                     tFlags,
  1258                     timeAfter(0),
  1347                     timeAfter(0),
  1259                     from,
  1348                     from,
  1260                     till, rtime,
  1349                     till, rtime,
  1261                     service,
  1350                     service,
  1262                     body.addresses
  1351                     body.addresses,
       
  1352                     enc_outPAs.toArray(new PAData[enc_outPAs.size()])
  1263                     );
  1353                     );
  1264             EncryptedData edata = new EncryptedData(ckey, enc_part.asn1Encode(),
  1354             EncryptedData edata = new EncryptedData(ckey, enc_part.asn1Encode(),
  1265                     KeyUsage.KU_ENC_AS_REP_PART);
  1355                     KeyUsage.KU_ENC_AS_REP_PART);
  1266             ASRep asRep = new ASRep(
  1356             ASRep asRep = new ASRep(
  1267                     outPAs.toArray(new PAData[outPAs.size()]),
  1357                     outPAs.toArray(new PAData[outPAs.size()]),
  1305                     + " " +ke.returnCodeMessage());
  1395                     + " " +ke.returnCodeMessage());
  1306             byte[] eData = null;
  1396             byte[] eData = null;
  1307             if (kerr == null) {
  1397             if (kerr == null) {
  1308                 if (ke.returnCode() == Krb5.KDC_ERR_PREAUTH_REQUIRED ||
  1398                 if (ke.returnCode() == Krb5.KDC_ERR_PREAUTH_REQUIRED ||
  1309                         ke.returnCode() == Krb5.KDC_ERR_PREAUTH_FAILED) {
  1399                         ke.returnCode() == Krb5.KDC_ERR_PREAUTH_FAILED) {
       
  1400                     outPAs.add(new PAData(Krb5.PA_ENC_TIMESTAMP, new byte[0]));
       
  1401                 }
       
  1402                 if (outPAs.size() > 0) {
  1310                     DerOutputStream bytes = new DerOutputStream();
  1403                     DerOutputStream bytes = new DerOutputStream();
  1311                     bytes.write(new PAData(Krb5.PA_ENC_TIMESTAMP, new byte[0]).asn1Encode());
       
  1312                     for (PAData p: outPAs) {
  1404                     for (PAData p: outPAs) {
  1313                         bytes.write(p.asn1Encode());
  1405                         bytes.write(p.asn1Encode());
  1314                     }
  1406                     }
  1315                     DerOutputStream temp = new DerOutputStream();
  1407                     DerOutputStream temp = new DerOutputStream();
  1316                     temp.write(DerValue.tag_Sequence, bytes);
  1408                     temp.write(DerValue.tag_Sequence, bytes);