/*
 * Copyright 2015 Open Networking Laboratory
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package org.onosproject.pcepio.protocol;

import org.jboss.netty.buffer.ChannelBuffer;
import org.onosproject.pcepio.exceptions.PcepParseException;
import org.onosproject.pcepio.protocol.ver1.PcepFactoryVer1;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public final class PcepFactories {

    protected static final Logger log = LoggerFactory.getLogger(PcepFactories.class);

    private static final GenericReader GENERIC_READER = new GenericReader();

    public static final byte SHIFT_FLAG = 5;

    private PcepFactories() {
    }

    /**
     * Returns the instance of PCEP Version.
     *
     * @param version PCEP version
     * @return PCEP version
     */
    public static PcepFactory getFactory(PcepVersion version) {
        switch (version) {
        case PCEP_1:
            return PcepFactoryVer1.INSTANCE;
        default:
            throw new IllegalArgumentException("Unknown version: " + version);
        }
    }

    private static class GenericReader implements PcepMessageReader<PcepMessage> {

        @Override
        public PcepMessage readFrom(ChannelBuffer bb) throws PcepParseException {

            if (!bb.readable()) {
                throw new PcepParseException("Empty message received");
            }

            /*
             * 0                   1                   2                   3
             * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
             * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
             * | Ver |  Flags  |                                               |
             * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
             *
             * Currently Version 1 is supported
             * Currently no flags are used, it is all ignored
             */

            byte packetVersion = bb.getByte(bb.readerIndex());
            packetVersion = (byte) (packetVersion >> SHIFT_FLAG);
            PcepFactory factory;

            switch (packetVersion) {

            case 1:
                factory = org.onosproject.pcepio.protocol.ver1.PcepFactoryVer1.INSTANCE;
                break;
            default:
                throw new IllegalArgumentException("Unknown Packet version: " + packetVersion);
            }
            return factory.getReader().readFrom(bb);
        }
    }

    /**
     * Returns GENERIC_READER.
     *
     * @return GENERIC_READER
     */
    public static PcepMessageReader<PcepMessage> getGenericReader() {
        return GENERIC_READER;
    }
}
