001    /*
002     *  Licensed to the Apache Software Foundation (ASF) under one
003     *  or more contributor license agreements.  See the NOTICE file
004     *  distributed with this work for additional information
005     *  regarding copyright ownership.  The ASF licenses this file
006     *  to you under the Apache License, Version 2.0 (the
007     *  "License"); you may not use this file except in compliance
008     *  with the License.  You may obtain a copy of the License at
009     *  
010     *    http://www.apache.org/licenses/LICENSE-2.0
011     *  
012     *  Unless required by applicable law or agreed to in writing,
013     *  software distributed under the License is distributed on an
014     *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
015     *  KIND, either express or implied.  See the License for the
016     *  specific language governing permissions and limitations
017     *  under the License. 
018     *  
019     */
020    package org.apache.directory.server.kerberos.shared.io.decoder;
021    
022    
023    import java.io.IOException;
024    import java.util.Enumeration;
025    
026    import org.apache.directory.server.kerberos.shared.messages.Encodable;
027    import org.apache.directory.server.kerberos.shared.messages.components.EncApRepPart;
028    import org.apache.directory.server.kerberos.shared.messages.components.EncApRepPartModifier;
029    import org.apache.directory.shared.asn1.der.ASN1InputStream;
030    import org.apache.directory.shared.asn1.der.DERApplicationSpecific;
031    import org.apache.directory.shared.asn1.der.DEREncodable;
032    import org.apache.directory.shared.asn1.der.DERGeneralizedTime;
033    import org.apache.directory.shared.asn1.der.DERInteger;
034    import org.apache.directory.shared.asn1.der.DERSequence;
035    import org.apache.directory.shared.asn1.der.DERTaggedObject;
036    
037    
038    /**
039     * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
040     * @version $Rev: 502338 $, $Date: 2007-02-01 11:59:43 -0800 (Thu, 01 Feb 2007) $
041     */
042    public class EncApRepPartDecoder implements Decoder, DecoderFactory
043    {
044        public Decoder getDecoder()
045        {
046            return new EncApRepPartDecoder();
047        }
048    
049    
050        public Encodable decode( byte[] encodedEncApRepPart ) throws IOException
051        {
052            ASN1InputStream ais = new ASN1InputStream( encodedEncApRepPart );
053    
054            DERApplicationSpecific app = ( DERApplicationSpecific ) ais.readObject();
055    
056            DERSequence apRepPart = ( DERSequence ) app.getObject();
057    
058            return decodeEncApRepPartSequence( apRepPart );
059        }
060    
061    
062        /**
063         * Decodes a {@link DERSequence} into a {@link EncApRepPart}.
064         * 
065         * EncAPRepPart    ::= [APPLICATION 27] SEQUENCE {
066         *         ctime           [0] KerberosTime,
067         *         cusec           [1] Microseconds,
068         *         subkey          [2] EncryptionKey OPTIONAL,
069         *         seq-number      [3] UInt32 OPTIONAL
070         * }
071         *
072         * @param sequence
073         * @return The {@link EncApRepPart}.
074         */
075        private EncApRepPart decodeEncApRepPartSequence( DERSequence sequence )
076        {
077            EncApRepPartModifier modifier = new EncApRepPartModifier();
078    
079            for ( Enumeration e = sequence.getObjects(); e.hasMoreElements(); )
080            {
081                DERTaggedObject object = ( DERTaggedObject ) e.nextElement();
082                int tag = object.getTagNo();
083                DEREncodable derObject = object.getObject();
084    
085                switch ( tag )
086                {
087                    case 0:
088                        DERGeneralizedTime tag0 = ( DERGeneralizedTime ) derObject;
089                        modifier.setClientTime( KerberosTimeDecoder.decode( tag0 ) );
090                        break;
091                    case 1:
092                        DERInteger tag1 = ( DERInteger ) derObject;
093                        modifier.setClientMicroSecond( new Integer( tag1.intValue() ) );
094                        break;
095                    case 2:
096                        DERSequence tag2 = ( DERSequence ) derObject;
097                        modifier.setSubSessionKey( EncryptionKeyDecoder.decode( tag2 ) );
098                        break;
099                    case 3:
100                        DERInteger tag3 = ( DERInteger ) derObject;
101                        modifier.setSequenceNumber( new Integer( tag3.intValue() ) );
102                        break;
103                }
104            }
105    
106            return modifier.getEncApRepPart();
107        }
108    }