Source Code Cross Referenced for DerOutputStream.java in  » 6.0-JDK-Modules-sun » security » sun » security » util » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » 6.0 JDK Modules sun » security » sun.security.util 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        /*
002:         * Copyright 1996-2006 Sun Microsystems, Inc.  All Rights Reserved.
003:         * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
004:         *
005:         * This code is free software; you can redistribute it and/or modify it
006:         * under the terms of the GNU General Public License version 2 only, as
007:         * published by the Free Software Foundation.  Sun designates this
008:         * particular file as subject to the "Classpath" exception as provided
009:         * by Sun in the LICENSE file that accompanied this code.
010:         *
011:         * This code is distributed in the hope that it will be useful, but WITHOUT
012:         * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
013:         * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
014:         * version 2 for more details (a copy is included in the LICENSE file that
015:         * accompanied this code).
016:         *
017:         * You should have received a copy of the GNU General Public License version
018:         * 2 along with this work; if not, write to the Free Software Foundation,
019:         * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
020:         *
021:         * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
022:         * CA 95054 USA or visit www.sun.com if you need additional information or
023:         * have any questions.
024:         */
025:
026:        package sun.security.util;
027:
028:        import java.io.FilterOutputStream;
029:        import java.io.ByteArrayOutputStream;
030:        import java.io.OutputStream;
031:        import java.io.IOException;
032:        import java.text.SimpleDateFormat;
033:        import java.util.Date;
034:        import java.util.TimeZone;
035:        import java.util.Vector;
036:        import java.util.Comparator;
037:        import java.util.Arrays;
038:        import java.math.BigInteger;
039:
040:        /**
041:         * Output stream marshaling DER-encoded data.  This is eventually provided
042:         * in the form of a byte array; there is no advance limit on the size of
043:         * that byte array.
044:         *
045:         * <P>At this time, this class supports only a subset of the types of
046:         * DER data encodings which are defined.  That subset is sufficient for
047:         * generating most X.509 certificates.
048:         *
049:         * @version 1.57
050:         *
051:         * @author David Brownell
052:         * @author Amit Kapoor
053:         * @author Hemma Prafullchandra
054:         */
055:        public class DerOutputStream extends ByteArrayOutputStream implements 
056:                DerEncoder {
057:            /**
058:             * Construct an DER output stream.
059:             *
060:             * @param size how large a buffer to preallocate.
061:             */
062:            public DerOutputStream(int size) {
063:                super (size);
064:            }
065:
066:            /**
067:             * Construct an DER output stream.
068:             */
069:            public DerOutputStream() {
070:            }
071:
072:            /**
073:             * Writes tagged, pre-marshaled data.  This calcuates and encodes
074:             * the length, so that the output data is the standard triple of
075:             * { tag, length, data } used by all DER values.
076:             *
077:             * @param tag the DER value tag for the data, such as
078:             *		<em>DerValue.tag_Sequence</em>
079:             * @param buf buffered data, which must be DER-encoded 
080:             */
081:            public void write(byte tag, byte[] buf) throws IOException {
082:                write(tag);
083:                putLength(buf.length);
084:                write(buf, 0, buf.length);
085:            }
086:
087:            /**
088:             * Writes tagged data using buffer-to-buffer copy.  As above,
089:             * this writes a standard DER record.  This is often used when
090:             * efficiently encapsulating values in sequences.
091:             *
092:             * @param tag the DER value tag for the data, such as
093:             *		<em>DerValue.tag_Sequence</em>
094:             * @param out buffered data
095:             */
096:            public void write(byte tag, DerOutputStream out) throws IOException {
097:                write(tag);
098:                putLength(out.count);
099:                write(out.buf, 0, out.count);
100:            }
101:
102:            /**
103:             * Writes implicitly tagged data using buffer-to-buffer copy.  As above,
104:             * this writes a standard DER record.  This is often used when
105:             * efficiently encapsulating implicitly tagged values.
106:             *   
107:             * @param tag the DER value of the context-specific tag that replaces
108:             * original tag of the value in the output, such as in
109:             * <pre>
110:             *          <em> <field> [N] IMPLICIT <type></em>
111:             * </pre>
112:             * For example, <em>FooLength [1] IMPLICIT INTEGER</em>, with value=4;
113:             * would be encoded as "81 01 04"  whereas in explicit
114:             * tagging it would be encoded as "A1 03 02 01 04".
115:             * Notice that the tag is A1 and not 81, this is because with
116:             * explicit tagging the form is always constructed. 
117:             * @param value original value being implicitly tagged
118:             */
119:            public void writeImplicit(byte tag, DerOutputStream value)
120:                    throws IOException {
121:                write(tag);
122:                write(value.buf, 1, value.count - 1);
123:            }
124:
125:            /**
126:             * Marshals pre-encoded DER value onto the output stream.
127:             */
128:            public void putDerValue(DerValue val) throws IOException {
129:                val.encode(this );
130:            }
131:
132:            /*
133:             * PRIMITIVES -- these are "universal" ASN.1 simple types.
134:             *
135:             * 	BOOLEAN, INTEGER, BIT STRING, OCTET STRING, NULL
136:             *	OBJECT IDENTIFIER, SEQUENCE(OF), SET(OF)
137:             *	PrintableString, T61String, IA5String, UTCTime
138:             */
139:
140:            /**
141:             * Marshals a DER boolean on the output stream.
142:             */
143:            public void putBoolean(boolean val) throws IOException {
144:                write(DerValue.tag_Boolean);
145:                putLength(1);
146:                if (val) {
147:                    write(0xff);
148:                } else {
149:                    write(0);
150:                }
151:            }
152:
153:            /**
154:             * Marshals a DER enumerated on the output stream.
155:             * @param i the enumerated value.
156:             */
157:            public void putEnumerated(int i) throws IOException {
158:                write(DerValue.tag_Enumerated);
159:                putIntegerContents(i);
160:            }
161:
162:            /**
163:             * Marshals a DER integer on the output stream.
164:             *
165:             * @param i the integer in the form of a BigInteger.
166:             */
167:            public void putInteger(BigInteger i) throws IOException {
168:                write(DerValue.tag_Integer);
169:                byte[] buf = i.toByteArray(); // least number  of bytes
170:                putLength(buf.length);
171:                write(buf, 0, buf.length);
172:            }
173:
174:            /**
175:             * Marshals a DER integer on the output stream.
176:             * @param i the integer in the form of an Integer.
177:             */
178:            public void putInteger(Integer i) throws IOException {
179:                putInteger(i.intValue());
180:            }
181:
182:            /**
183:             * Marshals a DER integer on the output stream.
184:             * @param i the integer.
185:             */
186:            public void putInteger(int i) throws IOException {
187:                write(DerValue.tag_Integer);
188:                putIntegerContents(i);
189:            }
190:
191:            private void putIntegerContents(int i) throws IOException {
192:
193:                byte[] bytes = new byte[4];
194:                int start = 0;
195:
196:                // Obtain the four bytes of the int
197:
198:                bytes[3] = (byte) (i & 0xff);
199:                bytes[2] = (byte) ((i & 0xff00) >>> 8);
200:                bytes[1] = (byte) ((i & 0xff0000) >>> 16);
201:                bytes[0] = (byte) ((i & 0xff000000) >>> 24);
202:
203:                // Reduce them to the least number of bytes needed to
204:                // represent this int
205:
206:                if (bytes[0] == 0xff) {
207:
208:                    // Eliminate redundant 0xff 
209:
210:                    for (int j = 0; j < 3; j++) {
211:                        if ((bytes[j] == 0xff)
212:                                && ((bytes[j + 1] & 0x80) == 0x80))
213:                            start++;
214:                        else
215:                            break;
216:                    }
217:                } else if (bytes[0] == 0x00) {
218:
219:                    // Eliminate redundant 0x00
220:
221:                    for (int j = 0; j < 3; j++) {
222:                        if ((bytes[j] == 0x00) && ((bytes[j + 1] & 0x80) == 0))
223:                            start++;
224:                        else
225:                            break;
226:                    }
227:                }
228:
229:                putLength(4 - start);
230:                for (int k = start; k < 4; k++)
231:                    write(bytes[k]);
232:            }
233:
234:            /**
235:             * Marshals a DER bit string on the output stream. The bit 
236:             * string must be byte-aligned.
237:             *
238:             * @param bits the bit string, MSB first
239:             */
240:            public void putBitString(byte[] bits) throws IOException {
241:                write(DerValue.tag_BitString);
242:                putLength(bits.length + 1);
243:                write(0); // all of last octet is used
244:                write(bits);
245:            }
246:
247:            /**
248:             * Marshals a DER bit string on the output stream.
249:             * The bit strings need not be byte-aligned.
250:             *
251:             * @param bits the bit string, MSB first
252:             */
253:            public void putUnalignedBitString(BitArray ba) throws IOException {
254:                byte[] bits = ba.toByteArray();
255:
256:                write(DerValue.tag_BitString);
257:                putLength(bits.length + 1);
258:                write(bits.length * 8 - ba.length()); // excess bits in last octet
259:                write(bits);
260:            }
261:
262:            /**
263:             * Marshals a truncated DER bit string on the output stream.
264:             * The bit strings need not be byte-aligned.
265:             *
266:             * @param bits the bit string, MSB first
267:             */
268:            public void putTruncatedUnalignedBitString(BitArray ba)
269:                    throws IOException {
270:                putUnalignedBitString(ba.truncate());
271:            }
272:
273:            /**
274:             * DER-encodes an ASN.1 OCTET STRING value on the output stream.
275:             *
276:             * @param octets the octet string
277:             */
278:            public void putOctetString(byte[] octets) throws IOException {
279:                write(DerValue.tag_OctetString, octets);
280:            }
281:
282:            /**
283:             * Marshals a DER "null" value on the output stream.  These are
284:             * often used to indicate optional values which have been omitted.
285:             */
286:            public void putNull() throws IOException {
287:                write(DerValue.tag_Null);
288:                putLength(0);
289:            }
290:
291:            /**
292:             * Marshals an object identifier (OID) on the output stream.
293:             * Corresponds to the ASN.1 "OBJECT IDENTIFIER" construct.
294:             */
295:            public void putOID(ObjectIdentifier oid) throws IOException {
296:                oid.encode(this );
297:            }
298:
299:            /**
300:             * Marshals a sequence on the output stream.  This supports both
301:             * the ASN.1 "SEQUENCE" (zero to N values) and "SEQUENCE OF"
302:             * (one to N values) constructs.
303:             */
304:            public void putSequence(DerValue[] seq) throws IOException {
305:                DerOutputStream bytes = new DerOutputStream();
306:                int i;
307:
308:                for (i = 0; i < seq.length; i++)
309:                    seq[i].encode(bytes);
310:
311:                write(DerValue.tag_Sequence, bytes);
312:            }
313:
314:            /**   
315:             * Marshals the contents of a set on the output stream without
316:             * ordering the elements.  Ok for BER encoding, but not for DER
317:             * encoding. 
318:             *
319:             * For DER encoding, use orderedPutSet() or orderedPutSetOf(). 
320:             */
321:            public void putSet(DerValue[] set) throws IOException {
322:                DerOutputStream bytes = new DerOutputStream();
323:                int i;
324:
325:                for (i = 0; i < set.length; i++)
326:                    set[i].encode(bytes);
327:
328:                write(DerValue.tag_Set, bytes);
329:            }
330:
331:            /**   
332:             * Marshals the contents of a set on the output stream.  Sets
333:             * are semantically unordered, but DER requires that encodings of
334:             * set elements be sorted into ascending lexicographical order
335:             * before being output.  Hence sets with the same tags and
336:             * elements have the same DER encoding.
337:             *
338:             * This method supports the ASN.1 "SET OF" construct, but not
339:             * "SET", which uses a different order.  
340:             */
341:            public void putOrderedSetOf(byte tag, DerEncoder[] set)
342:                    throws IOException {
343:                putOrderedSet(tag, set, lexOrder);
344:            }
345:
346:            /**   
347:             * Marshals the contents of a set on the output stream.  Sets
348:             * are semantically unordered, but DER requires that encodings of
349:             * set elements be sorted into ascending tag order
350:             * before being output.  Hence sets with the same tags and
351:             * elements have the same DER encoding.
352:             *
353:             * This method supports the ASN.1 "SET" construct, but not
354:             * "SET OF", which uses a different order.  
355:             */
356:            public void putOrderedSet(byte tag, DerEncoder[] set)
357:                    throws IOException {
358:                putOrderedSet(tag, set, tagOrder);
359:            }
360:
361:            /**
362:             *  Lexicographical order comparison on byte arrays, for ordering
363:             *  elements of a SET OF objects in DER encoding.
364:             */
365:            private static ByteArrayLexOrder lexOrder = new ByteArrayLexOrder();
366:
367:            /**
368:             *  Tag order comparison on byte arrays, for ordering elements of 
369:             *  SET objects in DER encoding.
370:             */
371:            private static ByteArrayTagOrder tagOrder = new ByteArrayTagOrder();
372:
373:            /**   
374:             * Marshals a the contents of a set on the output stream with the 
375:             * encodings of its sorted in increasing order.
376:             *
377:             * @param order the order to use when sorting encodings of components.
378:             */
379:            private void putOrderedSet(byte tag, DerEncoder[] set,
380:                    Comparator<byte[]> order) throws IOException {
381:                DerOutputStream[] streams = new DerOutputStream[set.length];
382:
383:                for (int i = 0; i < set.length; i++) {
384:                    streams[i] = new DerOutputStream();
385:                    set[i].derEncode(streams[i]);
386:                }
387:
388:                // order the element encodings
389:                byte[][] bufs = new byte[streams.length][];
390:                for (int i = 0; i < streams.length; i++) {
391:                    bufs[i] = streams[i].toByteArray();
392:                }
393:                Arrays.<byte[]> sort(bufs, order);
394:
395:                DerOutputStream bytes = new DerOutputStream();
396:                for (int i = 0; i < streams.length; i++) {
397:                    bytes.write(bufs[i]);
398:                }
399:                write(tag, bytes);
400:
401:            }
402:
403:            /**
404:             * Marshals a string as a DER encoded UTF8String.
405:             */
406:            public void putUTF8String(String s) throws IOException {
407:                writeString(s, DerValue.tag_UTF8String, "UTF8");
408:            }
409:
410:            /**
411:             * Marshals a string as a DER encoded PrintableString.
412:             */
413:            public void putPrintableString(String s) throws IOException {
414:                writeString(s, DerValue.tag_PrintableString, "ASCII");
415:            }
416:
417:            /**
418:             * Marshals a string as a DER encoded T61String.
419:             */
420:            public void putT61String(String s) throws IOException {
421:                /*
422:                 * Works for characters that are defined in both ASCII and
423:                 * T61.
424:                 */
425:                writeString(s, DerValue.tag_T61String, "ISO-8859-1");
426:            }
427:
428:            /**
429:             * Marshals a string as a DER encoded IA5String.
430:             */
431:            public void putIA5String(String s) throws IOException {
432:                writeString(s, DerValue.tag_IA5String, "ASCII");
433:            }
434:
435:            /**
436:             * Marshals a string as a DER encoded BMPString.
437:             */
438:            public void putBMPString(String s) throws IOException {
439:                writeString(s, DerValue.tag_BMPString, "UnicodeBigUnmarked");
440:            }
441:
442:            /**
443:             * Marshals a string as a DER encoded GeneralString.
444:             */
445:            public void putGeneralString(String s) throws IOException {
446:                writeString(s, DerValue.tag_GeneralString, "ASCII");
447:            }
448:
449:            /**
450:             * Private helper routine for writing DER encoded string values.
451:             * @param s the string to write
452:             * @param stringTag one of the DER string tags that indicate which 
453:             * encoding should be used to write the string out.
454:             * @param enc the name of the encoder that should be used corresponding
455:             * to the above tag.
456:             */
457:            private void writeString(String s, byte stringTag, String enc)
458:                    throws IOException {
459:
460:                byte[] data = s.getBytes(enc);
461:                write(stringTag);
462:                putLength(data.length);
463:                write(data);
464:            }
465:
466:            /**
467:             * Marshals a DER UTC time/date value.
468:             *
469:             * <P>YYMMDDhhmmss{Z|+hhmm|-hhmm} ... emits only using Zulu time
470:             * and with seconds (even if seconds=0) as per RFC 3280.
471:             */
472:            public void putUTCTime(Date d) throws IOException {
473:                putTime(d, DerValue.tag_UtcTime);
474:            }
475:
476:            /**
477:             * Marshals a DER Generalized Time/date value.
478:             *   
479:             * <P>YYYYMMDDhhmmss{Z|+hhmm|-hhmm} ... emits only using Zulu time
480:             * and with seconds (even if seconds=0) as per RFC 3280.
481:             */
482:            public void putGeneralizedTime(Date d) throws IOException {
483:                putTime(d, DerValue.tag_GeneralizedTime);
484:            }
485:
486:            /**
487:             * Private helper routine for marshalling a DER UTC/Generalized
488:             * time/date value. If the tag specified is not that for UTC Time
489:             * then it defaults to Generalized Time.
490:             * @param d the date to be marshalled
491:             * @param tag the tag for UTC Time or Generalized Time
492:             */
493:            private void putTime(Date d, byte tag) throws IOException {
494:
495:                /*
496:                 * Format the date.
497:                 */
498:
499:                TimeZone tz = TimeZone.getTimeZone("GMT");
500:                String pattern = null;
501:
502:                if (tag == DerValue.tag_UtcTime) {
503:                    pattern = "yyMMddHHmmss'Z'";
504:                } else {
505:                    tag = DerValue.tag_GeneralizedTime;
506:                    pattern = "yyyyMMddHHmmss'Z'";
507:                }
508:
509:                SimpleDateFormat sdf = new SimpleDateFormat(pattern);
510:                sdf.setTimeZone(tz);
511:                byte[] time = (sdf.format(d)).getBytes("ISO-8859-1");
512:
513:                /*
514:                 * Write the formatted date.
515:                 */
516:
517:                write(tag);
518:                putLength(time.length);
519:                write(time);
520:            }
521:
522:            /**
523:             * Put the encoding of the length in the stream.
524:             *   
525:             * @params len the length of the attribute.
526:             * @exception IOException on writing errors.
527:             */
528:            public void putLength(int len) throws IOException {
529:                if (len < 128) {
530:                    write((byte) len);
531:
532:                } else if (len < (1 << 8)) {
533:                    write((byte) 0x081);
534:                    write((byte) len);
535:
536:                } else if (len < (1 << 16)) {
537:                    write((byte) 0x082);
538:                    write((byte) (len >> 8));
539:                    write((byte) len);
540:
541:                } else if (len < (1 << 24)) {
542:                    write((byte) 0x083);
543:                    write((byte) (len >> 16));
544:                    write((byte) (len >> 8));
545:                    write((byte) len);
546:
547:                } else {
548:                    write((byte) 0x084);
549:                    write((byte) (len >> 24));
550:                    write((byte) (len >> 16));
551:                    write((byte) (len >> 8));
552:                    write((byte) len);
553:                }
554:            }
555:
556:            /**
557:             * Put the tag of the attribute in the stream.
558:             *   
559:             * @params class the tag class type, one of UNIVERSAL, CONTEXT,
560:             *                            APPLICATION or PRIVATE
561:             * @params form if true, the value is constructed, otherwise it is
562:             * primitive.
563:             * @params val the tag value
564:             */
565:            public void putTag(byte tagClass, boolean form, byte val) {
566:                byte tag = (byte) (tagClass | val);
567:                if (form) {
568:                    tag |= (byte) 0x20;
569:                }
570:                write(tag);
571:            }
572:
573:            /**
574:             *  Write the current contents of this <code>DerOutputStream</code>
575:             *  to an <code>OutputStream</code>.
576:             *
577:             *  @exception IOException on output error.
578:             */
579:            public void derEncode(OutputStream out) throws IOException {
580:                out.write(toByteArray());
581:            }
582:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.