001    /**
002     *  Licensed to the Apache Software Foundation (ASF) under one or more
003     *  contributor license agreements.  See the NOTICE file distributed with
004     *  this work for additional information regarding copyright ownership.
005     *  The ASF licenses this file to You under the Apache License, Version 2.0
006     *  (the "License"); you may not use this file except in compliance with
007     *  the License.  You may obtain a copy of the License at
008     *
009     *     http://www.apache.org/licenses/LICENSE-2.0
010     *
011     *  Unless required by applicable law or agreed to in writing, software
012     *  distributed under the License is distributed on an "AS IS" BASIS,
013     *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014     *  See the License for the specific language governing permissions and
015     *  limitations under the License.
016     */
017    
018    package org.apache.geronimo.crypto.asn1;
019    
020    import java.io.ByteArrayOutputStream;
021    import java.io.IOException;
022    import java.util.Enumeration;
023    import java.util.Vector;
024    
025    public abstract class ASN1OctetString
026        extends DERObject
027    {
028        byte[]  string;
029    
030        /**
031         * return an Octet String from a tagged object.
032         *
033         * @param obj the tagged object holding the object we want.
034         * @param explicit true if the object is meant to be explicitly
035         *              tagged false otherwise.
036         * @exception IllegalArgumentException if the tagged object cannot
037         *              be converted.
038         */
039        public static ASN1OctetString getInstance(
040            ASN1TaggedObject    obj,
041            boolean             explicit)
042        {
043            return getInstance(obj.getObject());
044        }
045    
046        /**
047         * return an Octet String from the given object.
048         *
049         * @param obj the object we want converted.
050         * @exception IllegalArgumentException if the object cannot be converted.
051         */
052        public static ASN1OctetString getInstance(
053            Object  obj)
054        {
055            if (obj == null || obj instanceof ASN1OctetString)
056            {
057                return (ASN1OctetString)obj;
058            }
059    
060            if (obj instanceof ASN1TaggedObject)
061            {
062                return getInstance(((ASN1TaggedObject)obj).getObject());
063            }
064    
065            if (obj instanceof ASN1Sequence)
066            {
067                Vector      v = new Vector();
068                Enumeration e = ((ASN1Sequence)obj).getObjects();
069    
070                while (e.hasMoreElements())
071                {
072                    v.addElement(e.nextElement());
073                }
074    
075                return new BERConstructedOctetString(v);
076            }
077    
078            throw new IllegalArgumentException("illegal object in getInstance: " + obj.getClass().getName());
079        }
080    
081        /**
082         * @param string the octets making up the octet string.
083         */
084        public ASN1OctetString(
085            byte[]  string)
086        {
087            this.string = string;
088        }
089    
090        public ASN1OctetString(
091            DEREncodable obj)
092        {
093            try
094            {
095                ByteArrayOutputStream   bOut = new ByteArrayOutputStream();
096                DEROutputStream         dOut = new DEROutputStream(bOut);
097    
098                dOut.writeObject(obj);
099                dOut.close();
100    
101                this.string = bOut.toByteArray();
102            }
103            catch (IOException e)
104            {
105                throw new IllegalArgumentException("Error processing object : " + e.getMessage(), e);
106            }
107        }
108    
109        public byte[] getOctets()
110        {
111            return string;
112        }
113    
114        public int hashCode()
115        {
116            byte[]  b = this.getOctets();
117            int     value = 0;
118    
119            for (int i = 0; i != b.length; i++)
120            {
121                value ^= (b[i] & 0xff) << (i % 4);
122            }
123    
124            return value;
125        }
126    
127        public boolean equals(
128            Object  o)
129        {
130            if (o == null || !(o instanceof DEROctetString))
131            {
132                return false;
133            }
134    
135            DEROctetString  other = (DEROctetString)o;
136    
137            byte[] b1 = other.getOctets();
138            byte[] b2 = this.getOctets();
139    
140            if (b1.length != b2.length)
141            {
142                return false;
143            }
144    
145            for (int i = 0; i != b1.length; i++)
146            {
147                if (b1[i] != b2[i])
148                {
149                    return false;
150                }
151            }
152    
153            return true;
154        }
155    
156        abstract void encode(DEROutputStream out)
157            throws IOException;
158    }