1:
37:
38:
39: package ;
40:
41: import ;
42: import ;
43: import ;
44: import ;
45: import ;
46: import ;
47:
48: import ;
49: import ;
50: import ;
51: import ;
52: import ;
53:
54: public class Extension
55: {
56: private static final Logger log = Configuration.DEBUG ?
57: Logger.getLogger(Extension.class.getName()) : null;
58:
61: protected final OID oid;
62:
63:
66: protected final boolean critical;
67:
68:
71: protected boolean isSupported;
72:
73:
76: protected final Value value;
77:
78:
81: protected byte[] encoded;
82:
83:
84:
85:
86: public Extension(byte[] encoded) throws IOException
87: {
88: this.encoded = (byte[]) encoded.clone();
89: DERReader der = new DERReader(encoded);
90:
91:
92: DERValue val = der.read();
93: if (Configuration.DEBUG)
94: log.fine("read val tag == " + val.getTag() + " len == " + val.getLength());
95: if (!val.isConstructed())
96: throw new IOException("malformed Extension");
97:
98:
99: val = der.read();
100: if (val.getTag() != DER.OBJECT_IDENTIFIER)
101: throw new IOException("expecting OBJECT IDENTIFIER");
102: oid = (OID) val.getValue();
103: if (Configuration.DEBUG)
104: log.fine("read oid == " + oid);
105:
106:
107: val = der.read();
108: if (val.getTag() == DER.BOOLEAN)
109: {
110: critical = ((Boolean) val.getValue()).booleanValue();
111: val = der.read();
112: }
113: else
114: critical = false;
115: if (Configuration.DEBUG)
116: log.fine("is critical == " + critical);
117:
118:
119: if (val.getTag() != DER.OCTET_STRING)
120: throw new IOException("expecting OCTET STRING");
121: byte[] encval = (byte[]) val.getValue();
122: isSupported = true;
123: if (oid.equals(AuthorityKeyIdentifier.ID))
124: {
125: value = new AuthorityKeyIdentifier(encval);
126: }
127: else if (oid.equals(SubjectKeyIdentifier.ID))
128: {
129: value = new SubjectKeyIdentifier(encval);
130: }
131: else if (oid.equals(KeyUsage.ID))
132: {
133: value = new KeyUsage(encval);
134: }
135: else if (oid.equals(PrivateKeyUsagePeriod.ID))
136: {
137: value = new PrivateKeyUsagePeriod(encval);
138: }
139: else if (oid.equals(CertificatePolicies.ID))
140: {
141: value = new CertificatePolicies(encval);
142: }
143: else if (oid.equals (PolicyConstraint.ID))
144: {
145: value = new PolicyConstraint (encval);
146: }
147: else if (oid.equals(PolicyMappings.ID))
148: {
149: value = new PolicyMappings(encval);
150: }
151: else if (oid.equals(SubjectAlternativeNames.ID))
152: {
153: value = new SubjectAlternativeNames(encval);
154: }
155: else if (oid.equals(IssuerAlternativeNames.ID))
156: {
157: value = new IssuerAlternativeNames(encval);
158: }
159: else if (oid.equals(BasicConstraints.ID))
160: {
161: value = new BasicConstraints(encval);
162: }
163: else if (oid.equals(ExtendedKeyUsage.ID))
164: {
165: value = new ExtendedKeyUsage(encval);
166: }
167: else if (oid.equals(CRLNumber.ID))
168: {
169: value = new CRLNumber(encval);
170: }
171: else if (oid.equals(ReasonCode.ID))
172: {
173: value = new ReasonCode(encval);
174: }
175: else if (oid.equals(NameConstraints.ID))
176: {
177: value = new NameConstraints(encval);
178: }
179: else
180: {
181: value = new Value(encval);
182: isSupported = false;
183: }
184: if (Configuration.DEBUG)
185: log.fine("read value == " + value);
186: }
187:
188: public Extension (final OID oid, final Value value, final boolean critical)
189: {
190: this.oid = oid;
191: this.value = value;
192: this.critical = critical;
193: isSupported = true;
194: }
195:
196:
197:
198:
199: public OID getOid()
200: {
201: return oid;
202: }
203:
204: public boolean isCritical()
205: {
206: return critical;
207: }
208:
209: public boolean isSupported()
210: {
211: return isSupported;
212: }
213:
214: public Value getValue()
215: {
216: return value;
217: }
218:
219: public byte[] getEncoded()
220: {
221: if (encoded == null)
222: encode();
223: return (byte[]) encoded.clone();
224: }
225:
226: public String toString()
227: {
228: return Extension.class.getName() + " [ id=" + oid + " critical=" +
229: critical + " value=" + value + " ]";
230: }
231:
232: public DERValue getDerValue()
233: {
234: List<DERValue> ext = new ArrayList<DERValue>(3);
235: ext.add(new DERValue(DER.OBJECT_IDENTIFIER, oid));
236: ext.add(new DERValue(DER.BOOLEAN, Boolean.valueOf(critical)));
237: ext.add(new DERValue(DER.OCTET_STRING, value.getEncoded()));
238: return new DERValue(DER.CONSTRUCTED|DER.SEQUENCE, ext);
239: }
240:
241:
242:
243:
244: private void encode()
245: {
246: encoded = getDerValue().getEncoded();
247: }
248:
249:
250:
251:
252: public static class Value
253: {
254:
255:
256:
257:
258: protected byte[] encoded;
259:
260:
261:
262:
263: public Value(byte[] encoded)
264: {
265: this.encoded = (byte[]) encoded.clone();
266: }
267:
268: protected Value() { }
269:
270:
271:
272:
273: public byte[] getEncoded()
274: {
275: return (byte[]) encoded;
276: }
277:
278: public int hashCode()
279: {
280: int result = 0;
281: for (int i = 0; i < encoded.length; ++i)
282: result = result * 31 + encoded[i];
283: return result;
284: }
285:
286: public boolean equals(Object o)
287: {
288: if (!(o instanceof Value))
289: return false;
290: return Arrays.equals(encoded, ((Value) o).encoded);
291: }
292:
293: public String toString()
294: {
295: return Util.toHexString(encoded, ':');
296: }
297: }
298: }