1package org.bouncycastle.asn1.cms; 2 3import org.bouncycastle.asn1.ASN1Encodable; 4import org.bouncycastle.asn1.ASN1EncodableVector; 5import org.bouncycastle.asn1.ASN1Object; 6import org.bouncycastle.asn1.ASN1ObjectIdentifier; 7import org.bouncycastle.asn1.ASN1Primitive; 8import org.bouncycastle.asn1.ASN1Sequence; 9import org.bouncycastle.asn1.ASN1Set; 10import org.bouncycastle.asn1.DERObjectIdentifier; 11import org.bouncycastle.asn1.DERSequence; 12 13/** 14 * <a href="http://tools.ietf.org/html/rfc5652#page-14">RFC 5652</a>: 15 * Attribute is a pair of OID (as type identifier) + set of values. 16 * <p> 17 * <pre> 18 * Attribute ::= SEQUENCE { 19 * attrType OBJECT IDENTIFIER, 20 * attrValues SET OF AttributeValue 21 * } 22 * 23 * AttributeValue ::= ANY 24 * </pre> 25 * <p> 26 * General rule on values is that same AttributeValue must not be included 27 * multiple times into the set. That is, if the value is a SET OF INTEGERs, 28 * then having same value repeated is wrong: (1, 1), but different values is OK: (1, 2). 29 * Normally the AttributeValue syntaxes are more complicated than that. 30 * <p> 31 * General rule of Attribute usage is that the {@link Attributes} containers 32 * must not have multiple Attribute:s with same attrType (OID) there. 33 */ 34public class Attribute 35 extends ASN1Object 36{ 37 private ASN1ObjectIdentifier attrType; 38 private ASN1Set attrValues; 39 40 /** 41 * Return an Attribute object from the given object. 42 * <p> 43 * Accepted inputs: 44 * <ul> 45 * <li> null → null 46 * <li> {@link Attribute} object 47 * <li> {@link org.bouncycastle.asn1.ASN1Sequence#getInstance(java.lang.Object) ASN1Sequence} input formats with Attribute structure inside 48 * </ul> 49 * 50 * @param o the object we want converted. 51 * @exception IllegalArgumentException if the object cannot be converted. 52 */ 53 public static Attribute getInstance( 54 Object o) 55 { 56 if (o instanceof Attribute) 57 { 58 return (Attribute)o; 59 } 60 61 if (o != null) 62 { 63 return new Attribute(ASN1Sequence.getInstance(o)); 64 } 65 66 return null; 67 } 68 69 private Attribute( 70 ASN1Sequence seq) 71 { 72 attrType = (ASN1ObjectIdentifier)seq.getObjectAt(0); 73 attrValues = (ASN1Set)seq.getObjectAt(1); 74 } 75 76 /** 77 * @deprecated use ASN1ObjectIdentifier 78 */ 79 public Attribute( 80 DERObjectIdentifier attrType, 81 ASN1Set attrValues) 82 { 83 this.attrType = new ASN1ObjectIdentifier(attrType.getId()); 84 this.attrValues = attrValues; 85 } 86 87 public Attribute( 88 ASN1ObjectIdentifier attrType, 89 ASN1Set attrValues) 90 { 91 this.attrType = attrType; 92 this.attrValues = attrValues; 93 } 94 95 public ASN1ObjectIdentifier getAttrType() 96 { 97 return attrType; 98 } 99 100 public ASN1Set getAttrValues() 101 { 102 return attrValues; 103 } 104 105 public ASN1Encodable[] getAttributeValues() 106 { 107 return attrValues.toArray(); 108 } 109 110 /** 111 * Produce an object suitable for an ASN1OutputStream. 112 */ 113 public ASN1Primitive toASN1Primitive() 114 { 115 ASN1EncodableVector v = new ASN1EncodableVector(); 116 117 v.add(attrType); 118 v.add(attrValues); 119 120 return new DERSequence(v); 121 } 122} 123