1b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallampackage org.bouncycastle.asn1; 2b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 3c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstromimport java.io.ByteArrayOutputStream; 4c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstromimport java.io.IOException; 5b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallamimport java.util.Enumeration; 6db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstromimport java.util.Vector; 7b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 8b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallamabstract public class ASN1Set 94c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom extends ASN1Primitive 10b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam{ 114c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom private Vector set = new Vector(); 124c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom private boolean isSorted = false; 13b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 14b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam /** 15b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * return an ASN1Set from the given object. 16b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * 17b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * @param obj the object we want converted. 18b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * @exception IllegalArgumentException if the object cannot be converted. 19b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam */ 20b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam public static ASN1Set getInstance( 21b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam Object obj) 22b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 23b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam if (obj == null || obj instanceof ASN1Set) 24b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 25b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam return (ASN1Set)obj; 26b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 274c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom else if (obj instanceof ASN1SetParser) 284c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 294c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return ASN1Set.getInstance(((ASN1SetParser)obj).toASN1Primitive()); 304c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 314c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom else if (obj instanceof byte[]) 324c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 334c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom try 344c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 354c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return ASN1Set.getInstance(ASN1Primitive.fromByteArray((byte[])obj)); 364c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 374c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom catch (IOException e) 384c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 394c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom throw new IllegalArgumentException("failed to construct set from byte[]: " + e.getMessage()); 404c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 414c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 424c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom else if (obj instanceof ASN1Encodable) 434c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 444c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Primitive primitive = ((ASN1Encodable)obj).toASN1Primitive(); 454c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 464c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom if (primitive instanceof ASN1Set) 474c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 484c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return (ASN1Set)primitive; 494c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 504c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 51b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 52c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom throw new IllegalArgumentException("unknown object in getInstance: " + obj.getClass().getName()); 53b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 54b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 55b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam /** 56b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * Return an ASN1 set from a tagged object. There is a special 57b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * case here, if an object appears to have been explicitly tagged on 58c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom * reading but we were expecting it to be implicitly tagged in the 59b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * normal course of events it indicates that we lost the surrounding 60b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * set - so we need to add it back (this will happen if the tagged 61b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * object is a sequence that contains other sequences). If you are 62b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * dealing with implicitly tagged sets you really <b>should</b> 63b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * be using this method. 64b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * 65b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * @param obj the tagged object. 66b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * @param explicit true if the object is meant to be explicitly tagged 67b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * false otherwise. 68b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * @exception IllegalArgumentException if the tagged object cannot 69b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam * be converted. 70b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam */ 71b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam public static ASN1Set getInstance( 72b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam ASN1TaggedObject obj, 73b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam boolean explicit) 74b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 75b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam if (explicit) 76b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 77b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam if (!obj.isExplicit()) 78b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 79b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam throw new IllegalArgumentException("object implicit - explicit expected."); 80b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 81b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 82b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam return (ASN1Set)obj.getObject(); 83b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 84b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam else 85b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 86b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam // 87b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam // constructed object which appears to be explicitly tagged 88b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam // and it's really implicit means we have to add the 894c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom // surrounding set. 90b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam // 91b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam if (obj.isExplicit()) 92b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 934c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom if (obj instanceof BERTaggedObject) 944c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 954c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return new BERSet(obj.getObject()); 964c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 974c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom else 984c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 994c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return new DLSet(obj.getObject()); 1004c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 101b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 102b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam else 103b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 104b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam if (obj.getObject() instanceof ASN1Set) 105b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 106b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam return (ASN1Set)obj.getObject(); 107b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 108b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 109b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam // 110b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam // in this case the parser returns a sequence, convert it 111b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam // into a set. 112b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam // 113b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam if (obj.getObject() instanceof ASN1Sequence) 114b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 115b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam ASN1Sequence s = (ASN1Sequence)obj.getObject(); 116b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 1174c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom if (obj instanceof BERTaggedObject) 118b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 1194c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return new BERSet(s.toArray()); 1204c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 1214c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom else 1224c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 1234c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return new DLSet(s.toArray()); 124b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 125b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 126b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 127b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 128b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 129c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom throw new IllegalArgumentException("unknown object in getInstance: " + obj.getClass().getName()); 130b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 131b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 1324c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom protected ASN1Set() 1334c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 1344c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 1354c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 1364c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom /** 1374c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom * create a sequence containing one object 1384c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom */ 1394c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom protected ASN1Set( 1404c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Encodable obj) 1414c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 1424c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom set.addElement(obj); 1434c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 1444c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 1454c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom /** 1464c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom * create a sequence containing a vector of objects. 1474c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom */ 1484c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom protected ASN1Set( 1494c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1EncodableVector v, 1504c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom boolean doSort) 1514c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 1524c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom for (int i = 0; i != v.size(); i++) 1534c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 1544c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom set.addElement(v.get(i)); 1554c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 1564c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 1574c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom if (doSort) 1584c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 1594c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom this.sort(); 1604c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 1614c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 1624c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 1634c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom /** 1644c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom * create a sequence containing a vector of objects. 1654c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom */ 1664c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom protected ASN1Set( 1674c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Encodable[] array, 1684c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom boolean doSort) 169b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 1704c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom for (int i = 0; i != array.length; i++) 1714c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 1724c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom set.addElement(array[i]); 1734c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 1744c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 1754c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom if (doSort) 1764c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 1774c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom this.sort(); 1784c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 179b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 180b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 181db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom public Enumeration getObjects() 182db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 183db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom return set.elements(); 184db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 185db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 186db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom /** 187db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom * return the object at the set position indicated by index. 188db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom * 189db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom * @param index the set number (starting at zero) of the object 190db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom * @return the object at the set position indicated by index. 191db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom */ 1924c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom public ASN1Encodable getObjectAt( 193db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom int index) 194db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 1954c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return (ASN1Encodable)set.elementAt(index); 196db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 197db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 198db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom /** 199db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom * return the number of objects in this set. 200db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom * 201db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom * @return the number of objects in this set. 202db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom */ 203db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom public int size() 204db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 205db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom return set.size(); 206db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 207b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 2086e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom public ASN1Encodable[] toArray() 2096e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom { 2106e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom ASN1Encodable[] values = new ASN1Encodable[this.size()]; 2116e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom 2126e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom for (int i = 0; i != this.size(); i++) 2136e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom { 2144c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom values[i] = this.getObjectAt(i); 2156e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom } 2166e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom 2176e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom return values; 2186e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom } 2196e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom 220c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom public ASN1SetParser parser() 221b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 222c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom final ASN1Set outer = this; 223c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 224c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom return new ASN1SetParser() 225b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 226c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom private final int max = size(); 227b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 228c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom private int index; 229c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 2304c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom public ASN1Encodable readObject() throws IOException 231c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom { 232c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom if (index == max) 233c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom { 234c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom return null; 235c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom } 236c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 2374c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Encodable obj = getObjectAt(index++); 238c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom if (obj instanceof ASN1Sequence) 239c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom { 240c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom return ((ASN1Sequence)obj).parser(); 241c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom } 242c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom if (obj instanceof ASN1Set) 243c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom { 244c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom return ((ASN1Set)obj).parser(); 245c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom } 246c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 247c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom return obj; 248c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom } 249c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 2504c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom public ASN1Primitive getLoadedObject() 2516e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom { 2526e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom return outer; 2536e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom } 2546e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom 2554c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom public ASN1Primitive toASN1Primitive() 256c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom { 257c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom return outer; 258c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom } 259c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom }; 260c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom } 261c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 262db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom public int hashCode() 263db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 264db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom Enumeration e = this.getObjects(); 265db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom int hashCode = size(); 266db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 267db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom while (e.hasMoreElements()) 268db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 269db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom Object o = getNext(e); 270db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom hashCode *= 17; 271db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 272db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom hashCode ^= o.hashCode(); 273db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 274db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 275db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom return hashCode; 276db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 277c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 2784c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Primitive toDERObject() 2794c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 2804c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom if (isSorted) 2814c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 2824c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Set derSet = new DERSet(); 2834c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 2844c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom derSet.set = this.set; 2854c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 2864c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return derSet; 2874c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 2884c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom else 2894c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 2904c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom Vector v = new Vector(); 2914c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 2924c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom for (int i = 0; i != set.size(); i++) 2934c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 2944c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom v.addElement(set.elementAt(i)); 2954c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 2964c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 2974c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Set derSet = new DERSet(); 2984c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 2994c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom derSet.set = v; 3004c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 3014c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom derSet.sort(); 3024c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 3034c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return derSet; 3044c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 3054c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 3064c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 3074c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Primitive toDLObject() 3084c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 3094c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Set derSet = new DLSet(); 3104c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 3114c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom derSet.set = this.set; 3124c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 3134c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return derSet; 3144c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 3154c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 316c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom boolean asn1Equals( 3174c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Primitive o) 318c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom { 319c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom if (!(o instanceof ASN1Set)) 320b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 321b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam return false; 322b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 323b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 324c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom ASN1Set other = (ASN1Set)o; 325b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 326b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam if (this.size() != other.size()) 327b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 328b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam return false; 329b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 330b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 331b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam Enumeration s1 = this.getObjects(); 332b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam Enumeration s2 = other.getObjects(); 333b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 334b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam while (s1.hasMoreElements()) 335b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 3364c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Encodable obj1 = getNext(s1); 3374c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Encodable obj2 = getNext(s2); 3386e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom 3394c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Primitive o1 = obj1.toASN1Primitive(); 3404c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Primitive o2 = obj2.toASN1Primitive(); 341c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 3426e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom if (o1 == o2 || o1.equals(o2)) 343b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam { 344c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom continue; 345b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 346c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 347c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom return false; 348b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 349b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 350b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam return true; 351b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam } 352b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 3534c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom private ASN1Encodable getNext(Enumeration e) 3546e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom { 3554c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Encodable encObj = (ASN1Encodable)e.nextElement(); 3566e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom 3576e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom // unfortunately null was allowed as a substitute for DER null 3586e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom if (encObj == null) 3596e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom { 3606e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom return DERNull.INSTANCE; 3616e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom } 3626e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom 3636e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom return encObj; 3646e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom } 3656e736056d64d0e33b26cf9f7c4e351b496241fdeBrian Carlstrom 366db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom /** 367db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom * return true if a <= b (arrays are assumed padded with zeros). 368db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom */ 369db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom private boolean lessThanOrEqual( 370db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom byte[] a, 371db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom byte[] b) 372db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 373db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom int len = Math.min(a.length, b.length); 374db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom for (int i = 0; i != len; ++i) 375db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 376db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom if (a[i] != b[i]) 377db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 378db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom return (a[i] & 0xff) < (b[i] & 0xff); 379db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 380db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 381db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom return len == a.length; 382db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 383b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam 384c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom private byte[] getEncoded( 3854c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom ASN1Encodable obj) 386c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom { 387c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom ByteArrayOutputStream bOut = new ByteArrayOutputStream(); 388c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom ASN1OutputStream aOut = new ASN1OutputStream(bOut); 389c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 390c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom try 391c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom { 392c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom aOut.writeObject(obj); 393c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom } 394c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom catch (IOException e) 395c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom { 396c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom throw new IllegalArgumentException("cannot encode object added to SET"); 397c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom } 398c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 399c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom return bOut.toByteArray(); 400c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom } 401c37f4a04ef89e73a39a59f3c5a179af8c8ab5974Brian Carlstrom 402db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom protected void sort() 403db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 4044c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom if (!isSorted) 405db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 4064c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom isSorted = true; 4074c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom if (set.size() > 1) 408db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 4094c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom boolean swapped = true; 4104c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom int lastSwap = set.size() - 1; 411db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 4124c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom while (swapped) 413db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 4144c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom int index = 0; 4154c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom int swapIndex = 0; 4164c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom byte[] a = getEncoded((ASN1Encodable)set.elementAt(0)); 417db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 4184c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom swapped = false; 4194c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 4204c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom while (index != lastSwap) 421db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 4224c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom byte[] b = getEncoded((ASN1Encodable)set.elementAt(index + 1)); 423db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 4244c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom if (lessThanOrEqual(a, b)) 4254c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 4264c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom a = b; 4274c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 4284c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom else 4294c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom { 4304c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom Object o = set.elementAt(index); 431db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 4324c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom set.setElementAt(set.elementAt(index + 1), index); 4334c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom set.setElementAt(o, index + 1); 4344c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 4354c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom swapped = true; 4364c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom swapIndex = index; 4374c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom } 4384c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom 4394c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom index++; 440db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 441db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 4424c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom lastSwap = swapIndex; 443db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 444db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 445db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 446db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 447db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 4484c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom boolean isConstructed() 449db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 4504c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return true; 451db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 452db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 4534c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom abstract void encode(ASN1OutputStream out) 454db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom throws IOException; 455db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom 456db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom public String toString() 457db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom { 4584c111300c39cb2e27f07fc2ae3b00e23ed4443b2Brian Carlstrom return set.toString(); 459db9f6e2562dff550a3c62aeb7c96e72fc40d1a06Brian Carlstrom } 460b61a96e7ef1a78acf013bbf08fe537e5b5f129caPeter Hallam} 461