1package org.bouncycastle.asn1;
2
3import java.io.ByteArrayOutputStream;
4import java.io.IOException;
5
6/**
7 * Base class for an application specific object
8 */
9public class DERApplicationSpecific
10    extends DERObject
11{
12    private int       tag;
13    private byte[]    octets;
14
15    public DERApplicationSpecific(
16        int        tag,
17        byte[]    octets)
18    {
19        this.tag = tag;
20        this.octets = octets;
21    }
22
23    public DERApplicationSpecific(
24        int                  tag,
25        DEREncodable         object)
26        throws IOException
27    {
28        this.tag = tag | DERTags.CONSTRUCTED;
29
30        ByteArrayOutputStream baos = new ByteArrayOutputStream();
31        DEROutputStream dos = new DEROutputStream(baos);
32
33        dos.writeObject(object);
34
35        this.octets = baos.toByteArray();
36    }
37
38    public boolean isConstructed()
39    {
40        return (tag & DERTags.CONSTRUCTED) != 0;
41    }
42
43    public byte[] getContents()
44    {
45        return octets;
46    }
47
48    public int getApplicationTag()
49    {
50        return tag & 0x1F;
51    }
52
53    public DERObject getObject()
54        throws IOException
55    {
56        return new ASN1InputStream(getContents()).readObject();
57    }
58
59    /* (non-Javadoc)
60     * @see org.bouncycastle.asn1.DERObject#encode(org.bouncycastle.asn1.DEROutputStream)
61     */
62    void encode(DEROutputStream out) throws IOException
63    {
64        out.writeEncoded(DERTags.APPLICATION | tag, octets);
65    }
66
67    public boolean equals(
68            Object o)
69    {
70        if ((o == null) || !(o instanceof DERApplicationSpecific))
71        {
72            return false;
73        }
74
75        DERApplicationSpecific other = (DERApplicationSpecific)o;
76
77        if (tag != other.tag)
78        {
79            return false;
80        }
81
82        if (octets.length != other.octets.length)
83        {
84            return false;
85        }
86
87        for (int i = 0; i < octets.length; i++)
88        {
89            if (octets[i] != other.octets[i])
90            {
91                return false;
92            }
93        }
94
95        return true;
96    }
97
98    public int hashCode()
99    {
100        byte[]  b = this.getContents();
101        int     value = 0;
102
103        for (int i = 0; i != b.length; i++)
104        {
105            value ^= (b[i] & 0xff) << (i % 4);
106        }
107
108        return value ^ this.getApplicationTag();
109    }
110}
111