blob: 30ea6b8fb88eab549af95c32926d50ace15b8b90 [file] [log] [blame]
J. Duke319a3b92007-12-01 00:00:00 +00001/*
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 it
5 * under the terms of the GNU General Public License version 2 only, as
6 * published by the Free Software Foundation. Sun designates this
7 * particular file as subject to the "Classpath" exception as provided
8 * by Sun in the LICENSE file that accompanied this code.
9 *
10 * This code is distributed in the hope that it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
13 * version 2 for more details (a copy is included in the LICENSE file that
14 * accompanied this code).
15 *
16 * You should have received a copy of the GNU General Public License version
17 * 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 Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
21 * CA 95054 USA or visit www.sun.com if you need additional information or
22 * have any questions.
23 */
24
25/*
26 *
27 * (C) Copyright IBM Corp. 1999 All Rights Reserved.
28 * Copyright 1997 The Open Group Research Institute. All rights reserved.
29 */
30
31package sun.security.krb5.internal;
32
33import sun.security.krb5.PrincipalName;
34import sun.security.krb5.EncryptedData;
35import sun.security.krb5.Asn1Exception;
36import sun.security.krb5.Realm;
37import sun.security.krb5.RealmException;
38import sun.security.util.*;
39import java.io.IOException;
40import java.math.BigInteger;
41
42/**
43 * Implements the ASN.1 Ticket type.
44 *
45 * <xmp>
46 * Ticket ::= [APPLICATION 1] SEQUENCE {
47 * tkt-vno [0] INTEGER (5),
48 * realm [1] Realm,
49 * sname [2] PrincipalName,
50 * enc-part [3] EncryptedData -- EncTicketPart
51 * }
52 * </xmp>
53 *
54 * <p>
55 * This definition reflects the Network Working Group RFC 4120
56 * specification available at
57 * <a href="http://www.ietf.org/rfc/rfc4120.txt">
58 * http://www.ietf.org/rfc/rfc4120.txt</a>.
59 */
60
61public class Ticket implements Cloneable {
62 public int tkt_vno;
63 public Realm realm;
64 public PrincipalName sname;
65 public EncryptedData encPart;
66
67 private Ticket() {
68 }
69
70 public Object clone() {
71 Ticket new_ticket = new Ticket();
72 new_ticket.realm = (Realm)realm.clone();
73 new_ticket.sname = (PrincipalName)sname.clone();
74 new_ticket.encPart = (EncryptedData)encPart.clone();
75 new_ticket.tkt_vno = tkt_vno;
76 return new_ticket;
77 }
78
79 public Ticket(
80 Realm new_realm,
81 PrincipalName new_sname,
82 EncryptedData new_encPart
83 ) {
84 tkt_vno = Krb5.TICKET_VNO;
85 realm = new_realm;
86 sname = new_sname;
87 encPart = new_encPart;
88 }
89
90 public Ticket(byte[] data) throws Asn1Exception,
91 RealmException, KrbApErrException, IOException {
92 init(new DerValue(data));
93 }
94
95 public Ticket(DerValue encoding) throws Asn1Exception,
96 RealmException, KrbApErrException, IOException {
97 init(encoding);
98 }
99
100 /**
101 * Initializes a Ticket object.
102 * @param encoding a single DER-encoded value.
103 * @exception Asn1Exception if an error occurs while decoding an ASN1 encoded data.
104 * @exception IOException if an I/O error occurs while reading encoded data.
105 * @exception KrbApErrException if the value read from the DER-encoded data stream does not match the pre-defined value.
106 * @exception RealmException if an error occurs while parsing a Realm object.
107 */
108
109 private void init(DerValue encoding) throws Asn1Exception,
110 RealmException, KrbApErrException, IOException {
111 DerValue der;
112 DerValue subDer;
113 if (((encoding.getTag() & (byte)0x1F) != Krb5.KRB_TKT)
114 || (encoding.isApplication() != true)
115 || (encoding.isConstructed() != true))
116 throw new Asn1Exception(Krb5.ASN1_BAD_ID);
117 der = encoding.getData().getDerValue();
118 if (der.getTag() != DerValue.tag_Sequence)
119 throw new Asn1Exception(Krb5.ASN1_BAD_ID);
120 subDer = der.getData().getDerValue();
121 if ((subDer.getTag() & (byte)0x1F) != (byte)0x00)
122 throw new Asn1Exception(Krb5.ASN1_BAD_ID);
123 tkt_vno = subDer.getData().getBigInteger().intValue();
124 if (tkt_vno != Krb5.TICKET_VNO)
125 throw new KrbApErrException(Krb5.KRB_AP_ERR_BADVERSION);
126 realm = Realm.parse(der.getData(), (byte)0x01, false);
127 sname = PrincipalName.parse(der.getData(), (byte)0x02, false);
128 encPart = EncryptedData.parse(der.getData(), (byte)0x03, false);
129 if (der.getData().available() > 0)
130 throw new Asn1Exception(Krb5.ASN1_BAD_ID);
131 }
132
133 /**
134 * Encodes a Ticket object.
135 * @return byte array of encoded ticket object.
136 * @exception Asn1Exception if an error occurs while decoding an ASN1 encoded data.
137 * @exception IOException if an I/O error occurs while reading encoded data.
138 */
139 public byte[] asn1Encode() throws Asn1Exception, IOException {
140 DerOutputStream bytes = new DerOutputStream();
141 DerOutputStream temp = new DerOutputStream();
142 DerValue der[] = new DerValue[4];
143 temp.putInteger(BigInteger.valueOf(tkt_vno));
144 bytes.write(DerValue.createTag(DerValue.TAG_CONTEXT, true, (byte)0x00), temp);
145 bytes.write(DerValue.createTag(DerValue.TAG_CONTEXT, true, (byte)0x01), realm.asn1Encode());
146 bytes.write(DerValue.createTag(DerValue.TAG_CONTEXT, true, (byte)0x02), sname.asn1Encode());
147 bytes.write(DerValue.createTag(DerValue.TAG_CONTEXT, true, (byte)0x03), encPart.asn1Encode());
148 temp = new DerOutputStream();
149 temp.write(DerValue.tag_Sequence, bytes);
150 DerOutputStream ticket = new DerOutputStream();
151 ticket.write(DerValue.createTag(DerValue.TAG_APPLICATION, true, (byte)0x01), temp);
152 return ticket.toByteArray();
153 }
154
155 /**
156 * Parse (unmarshal) a Ticket from a DER input stream. This form
157 * parsing might be used when expanding a value which is part of
158 * a constructed sequence and uses explicitly tagged type.
159 *
160 * @exception Asn1Exception on error.
161 * @param data the Der input stream value, which contains one or more marshaled value.
162 * @param explicitTag tag number.
163 * @param optional indicate if this data field is optional
164 * @return an instance of Ticket.
165 */
166 public static Ticket parse(DerInputStream data, byte explicitTag, boolean optional) throws Asn1Exception, IOException, RealmException, KrbApErrException {
167 if ((optional) && (((byte)data.peekByte() & (byte)0x1F)!= explicitTag))
168 return null;
169 DerValue der = data.getDerValue();
170 if (explicitTag != (der.getTag() & (byte)0x1F)) {
171 throw new Asn1Exception(Krb5.ASN1_BAD_ID);
172 }
173 else {
174 DerValue subDer = der.getData().getDerValue();
175 return new Ticket(subDer);
176 }
177 }
178
179
180}