2 * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
8 package org.opendaylight.protocol.pcep.impl;
10 import java.util.Arrays;
12 import org.opendaylight.protocol.util.ByteArray;
13 import org.slf4j.Logger;
14 import org.slf4j.LoggerFactory;
16 import com.google.common.primitives.UnsignedBytes;
19 * Header parser for {@link org.opendaylight.protocol.pcep.PCEPMessage PCEPMessage}
21 public final class PCEPMessageHeader {
23 public static final Logger logger = LoggerFactory.getLogger(PCEPMessageHeader.class);
26 * lengths of fields in bytes
28 private static final int VER_FLAGS_MF_LENGTH = 1;
29 private static final int TYPE_F_LENGTH = 1;
30 private static final int LENGTH_F_LENGTH = 2;
33 * lengths of subfields inside multi-field in bits
35 private static final int VERSION_SF_LENGTH = 3;
38 * offsets of field in bytes
40 private static final int VER_FLAGS_MF_OFFSET = 0;
41 private static final int TYPE_F_OFFSET = VER_FLAGS_MF_LENGTH + VER_FLAGS_MF_OFFSET;
42 private static final int LENGTH_F_OFFSET = TYPE_F_LENGTH + TYPE_F_OFFSET;
45 * offsets of subfields inside multi-filed in bits
48 private static final int VERSION_SF_OFFSET = 0;
51 * COMMON HEADER LENGTH
53 public static final int COMMON_HEADER_LENGTH = VER_FLAGS_MF_LENGTH + TYPE_F_LENGTH + LENGTH_F_LENGTH;
55 private final int type;
56 private final int length;
57 private final int version;
59 public PCEPMessageHeader(final int type, final int length, final int version) {
62 this.version = version;
65 public static PCEPMessageHeader fromBytes(final byte[] bytes) {
67 throw new IllegalArgumentException("Array of bytes is mandatory");
70 logger.trace("Attempt to parse message header: {}", ByteArray.bytesToHexString(bytes));
72 if (bytes.length < COMMON_HEADER_LENGTH) {
73 throw new IllegalArgumentException("Too few bytes in passed array. Passed: " + bytes.length + "; Expected: >= " + COMMON_HEADER_LENGTH + ".");
76 final int type = UnsignedBytes.toInt(bytes[TYPE_F_OFFSET]);
78 final int length = ByteArray.bytesToInt(Arrays.copyOfRange(bytes,
79 LENGTH_F_OFFSET, LENGTH_F_OFFSET + LENGTH_F_LENGTH));
81 final int version = ByteArray.copyBitsRange(bytes[VER_FLAGS_MF_OFFSET], VERSION_SF_OFFSET, VERSION_SF_LENGTH);
83 final PCEPMessageHeader ret = new PCEPMessageHeader(type, length, version);
85 logger.trace("Message header was parsed. {}", ret);
89 public byte[] toBytes() {
90 final byte[] retBytes = new byte[COMMON_HEADER_LENGTH];
93 retBytes[VER_FLAGS_MF_OFFSET] = (byte) (this.version << (Byte.SIZE - VERSION_SF_LENGTH));
96 retBytes[TYPE_F_OFFSET] = (byte) this.type;
99 System.arraycopy(ByteArray.intToBytes(this.length), Integer.SIZE / Byte.SIZE - LENGTH_F_LENGTH, retBytes, LENGTH_F_OFFSET, LENGTH_F_LENGTH);
104 public int getLength() {
108 public int getVersion() {
112 public int getType() {
117 public String toString() {
118 final StringBuilder builder = new StringBuilder();
119 builder.append("PCEPMessageHeader [type=");
120 builder.append(this.type);
121 builder.append(", length=");
122 builder.append(this.length);
123 builder.append(", version=");
124 builder.append(this.version);
126 return builder.toString();