BGP Monitoring in ONOS.
Jira Id: ONOS-8136

Implement bgpmonitoring Api.

Change-Id: I3542cf63b3b3ec604d293c166dbf413b7c158ac7
diff --git a/apps/bgpmonitoring/api/BUILD b/apps/bgpmonitoring/api/BUILD
new file mode 100644
index 0000000..6109d51
--- /dev/null
+++ b/apps/bgpmonitoring/api/BUILD
@@ -0,0 +1,10 @@
+COMPILE_DEPS = CORE_DEPS + [
+    "//core/store/serializers:onos-core-serializers",
+    "//protocols/bgp/bgpio:onos-protocols-bgp-bgpio",
+    "@io_netty_netty//jar",
+]
+
+osgi_jar_with_tests(
+    test_deps = TEST_ADAPTERS,
+    deps = COMPILE_DEPS,
+)
diff --git a/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpController.java b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpController.java
new file mode 100644
index 0000000..d36e9a9
--- /dev/null
+++ b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpController.java
@@ -0,0 +1,42 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.bgpmonitoring;
+
+/**
+ * Abstraction of an BMP controller. It handles BMP messages from BMP routers
+ */
+public interface BmpController {
+
+    /**
+     * Start listening bmp messages from bmp router.
+     */
+    void startListener();
+
+    /**
+     * Stop listening bmp messages from bmp router.
+     */
+    void closeListener();
+
+    /**
+     * Process bmp message and notify the appropriate listeners.
+     *
+     * @param message   the message to process.
+     * @throws BmpParseException on data processing error
+     */
+    void processBmpPacket(BmpMessage message) throws BmpParseException;
+
+}
diff --git a/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpParseException.java b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpParseException.java
new file mode 100644
index 0000000..9c48547
--- /dev/null
+++ b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpParseException.java
@@ -0,0 +1,62 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.bgpmonitoring;
+
+
+/**
+ * Custom Exception for BMP IO.
+ */
+public class BmpParseException extends Exception {
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * Default constructor to create a new exception.
+     */
+    public BmpParseException() {
+        super();
+    }
+
+    /**
+     * Constructor to create exception from message and cause.
+     *
+     * @param message  the detail of exception in string
+     * @param cause underlying cause of the error
+     */
+    public BmpParseException(final String message, final Throwable cause) {
+        super(message, cause);
+    }
+
+    /**
+     * Constructor to create exception from message.
+     *
+     * @param message the detail of exception in string
+     */
+    public BmpParseException(final String message) {
+        super(message);
+    }
+
+    /**
+     * Constructor to create exception from cause.
+     *
+     * @param cause underlying cause of the error
+     */
+    public BmpParseException(final Throwable cause) {
+        super(cause);
+    }
+
+}
diff --git a/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpType.java b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpType.java
new file mode 100644
index 0000000..93a94fe
--- /dev/null
+++ b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpType.java
@@ -0,0 +1,58 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.bgpmonitoring;
+
+/**
+ * Enum to Provide the Different types of BMP messages.
+ */
+public enum BmpType {
+
+    ROUTE_MONITORING((byte) 0x0),
+
+    STATISTICS_REPORT((byte) 0x1),
+
+    PEER_DOWN_NOTIFICATION((byte) 0x2),
+
+    PEER_UP_NOTIFICATION((byte) 0x3),
+
+    INITIATION_MESSAGE((byte) 0x4),
+
+    TERMINATION_MESSAGE((byte) 0x5),
+
+    ROUTE_MIRRORING_MESSAGE((byte) 0x6);
+
+    private final byte value;
+
+    /**
+     * Assign value with the value val as the types of BMP message.
+     *
+     * @param val type of BMP message
+     */
+    BmpType(byte val) {
+        value = val;
+    }
+
+
+    /**
+     * Returns value as type of BMP message.
+     *
+     * @return value type of BMP message
+     */
+    public byte getType() {
+        return value;
+    }
+}
diff --git a/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpVersion.java b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpVersion.java
new file mode 100644
index 0000000..4d1da8f9
--- /dev/null
+++ b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/BmpVersion.java
@@ -0,0 +1,46 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.bgpmonitoring;
+
+
+/**
+ * Enum to provide BMP Message Version.
+ */
+public enum BmpVersion {
+
+    BMP_3(3);
+
+    public final int packetVersion;
+
+    /**
+     * Assign BMP PacketVersion with specified packetVersion.
+     *
+     * @param packetVersion version of BMP
+     */
+    BmpVersion(final int packetVersion) {
+        this.packetVersion = packetVersion;
+    }
+
+    /**
+     * Returns Packet version of BMP Message.
+     *
+     * @return packetVersion
+     */
+    public int getPacketVersion() {
+        return packetVersion;
+    }
+}
\ No newline at end of file
diff --git a/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/MirroringType.java b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/MirroringType.java
new file mode 100644
index 0000000..7fcf4cc
--- /dev/null
+++ b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/MirroringType.java
@@ -0,0 +1,48 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.bgpmonitoring;
+
+/**
+ * Enum to Provide the Different types of BMP mirroring message.
+ */
+public enum MirroringType {
+
+    BGP_MESSAGE(0),
+
+    INFORMATION(1);
+
+    private final int value;
+
+    /**
+     * Assign value with the value val as the types of BMP mirroring message.
+     *
+     * @param val type of BMP mirroring message
+     */
+    MirroringType(int val) {
+        value = val;
+    }
+
+
+    /**
+     * Returns value as type of BMP mirroring message.
+     *
+     * @return value type of BMP mirroring message
+     */
+    public int getType() {
+        return value;
+    }
+}
diff --git a/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/PeerDownReason.java b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/PeerDownReason.java
new file mode 100644
index 0000000..b6e0e8e
--- /dev/null
+++ b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/PeerDownReason.java
@@ -0,0 +1,52 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.bgpmonitoring;
+
+/**
+ * Enum to Provide the Different types of BMP peer down reasons.
+ */
+public enum PeerDownReason {
+
+    LOCAL_SYSTEM_CLOSED_SESSION_WITH_NOTIFICATION((byte) 0x01),
+
+    LOCAL_SYSTEM_CLOSED_SESSION_WITHOUT_NOTIFICATION((byte) 0x02),
+
+    REMOTE_SYSTEM_CLOSED_SESSION_WITH_NOTIFICATION((byte) 0x03),
+
+    REMOTE_SYSTEM_CLOSED_SESSION_WITHOUT_NOTIFICATION((byte) 0x04);
+
+
+    private final byte value;
+
+    /**
+     * Assign value with the value val as the types of BMP peer down reasons.
+     *
+     * @param val type of BMP peer down reasons
+     */
+    PeerDownReason(byte val) {
+        value = val;
+    }
+
+    /**
+     * Returns value as type of BMP peer down reasons.
+     *
+     * @return value type of BMP peer down reasons
+     */
+    public byte getReason() {
+        return value;
+    }
+}
diff --git a/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/StatsType.java b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/StatsType.java
new file mode 100644
index 0000000..9ab93d8
--- /dev/null
+++ b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/StatsType.java
@@ -0,0 +1,74 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.bgpmonitoring;
+
+/**
+ * Enum to Provide the Different types of BMP stats.
+ */
+public enum StatsType {
+
+    PREFIXES_REJECTED(0),
+
+    DUPLICATE_PREFIX(1),
+
+    DUPLICATE_WITHDRAW(2),
+
+    CLUSTER_LIST(3),
+
+    AS_PATH(4),
+
+    ORIGINATOR_ID(5),
+
+    AS_CONFED(6),
+
+    ADJ_RIB_IN(7),
+
+    LOC_RIB(8),
+
+    ADJ_RIB_IN_AFI_SAFI(9),
+
+    LOC_RIB_AFI_SAFI(10),
+
+    UPDATES_SUBJECTED_WITHDRAW(11),
+
+    PREFIXES_SUBJECTED_WITHDRAW(12),
+
+    DUPLICATE_UPDATE_MESSAGES(13),
+
+    JNX_ADJ_RIB_IN(17);
+
+
+    private final int value;
+
+    /**
+     * Assign value with the value val as the types of BMP stats.
+     *
+     * @param val type of BMP stats
+     */
+    StatsType(int val) {
+        value = val;
+    }
+
+    /**
+     * Returns value as type of BMP stats.
+     *
+     * @return value type of BMP stats
+     */
+    public int getType() {
+        return value;
+    }
+}
diff --git a/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/TerminationType.java b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/TerminationType.java
new file mode 100644
index 0000000..5e7ad01
--- /dev/null
+++ b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/TerminationType.java
@@ -0,0 +1,47 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.bgpmonitoring;
+
+/**
+ * Enum to Provide the Different types of BMP termination message.
+ */
+public enum TerminationType {
+
+    UTF8_STRING(0),
+
+    REASON(1);
+
+    private final int value;
+
+    /**
+     * Assign value with the value val as the types of BMP termination message.
+     *
+     * @param val type of BMP termination message
+     */
+    TerminationType(int val) {
+        value = val;
+    }
+
+    /**
+     * Returns value as type of BMP termination message.
+     *
+     * @return value type of BMP termination message
+     */
+    public int getType() {
+        return value;
+    }
+}
diff --git a/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/package-info.java b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/package-info.java
new file mode 100644
index 0000000..492c271
--- /dev/null
+++ b/apps/bgpmonitoring/api/src/main/java/org/onosproject/bgpmonitoring/package-info.java
@@ -0,0 +1,20 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.
+ */
+
+/**
+ * BMP api components.
+ */
+package org.onosproject.bgpmonitoring;
\ No newline at end of file
diff --git a/utils/misc/src/main/java/org/onlab/packet/bmp/Bmp.java b/utils/misc/src/main/java/org/onlab/packet/bmp/Bmp.java
new file mode 100644
index 0000000..b64e34b
--- /dev/null
+++ b/utils/misc/src/main/java/org/onlab/packet/bmp/Bmp.java
@@ -0,0 +1,174 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.onlab.packet.bmp;
+
+import com.google.common.base.MoreObjects;
+import org.onlab.packet.BasePacket;
+import org.onlab.packet.Deserializer;
+
+import java.nio.ByteBuffer;
+
+import static org.onlab.packet.PacketUtils.checkInput;
+
+/**
+ * The following common header appears in all BMP messages.  The rest of
+ * the data in a BMP message is dependent on the Message Type field in
+ * the common header.
+ * <p>
+ * Version (1 byte): Indicates the BMP version.  This is set to '3'
+ * for all messages defined in this specification. ('1' and '2' were
+ * used by draft versions of this document.)  Version 0 is reserved
+ * and MUST NOT be sent.
+ * <p>
+ * Message Length (4 bytes): Length of the message in bytes
+ * (including headers, data, and encapsulated messages, if any).
+ * <p>
+ * Message Type (1 byte): This identifies the type of the BMP
+ * message.  A BMP implementation MUST ignore unrecognized message
+ * types upon receipt.
+ * <p>
+ * Type = 0: Route Monitoring
+ * Type = 1: Statistics Report
+ * Type = 2: Peer Down Notification
+ * Type = 3: Peer Up Notification
+ * Type = 4: Initiation Message
+ * Type = 5: Termination Message
+ * Type = 6: Route Mirroring Message
+ */
+public class Bmp extends BasePacket {
+
+    /*
+
+      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
+     +-+-+-+-+-+-+-+-+
+     |    Version    |
+     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+     |                        Message Length                         |
+     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+     |   Msg. Type   |
+     +---------------+
+
+     */
+
+
+    public static final short DEFAULT_HEADER_LENGTH = 6;
+    public static final int DEFAULT_PACKET_MINIMUM_LENGTH = 4;
+
+    protected byte version;
+    protected byte type;
+    protected int length;
+
+
+    /**
+     * Sets version field.
+     *
+     * @param version message version field
+     */
+    public void setVersion(byte version) {
+        this.version = version;
+    }
+
+    /**
+     * Sets message type.
+     *
+     * @param type message type
+     */
+    public void setType(byte type) {
+        this.type = type;
+    }
+
+    /**
+     * Sets message length.
+     *
+     * @param length message length
+     */
+    public void setLength(int length) {
+        this.length = length;
+    }
+
+    /**
+     * Returns message length.
+     *
+     * @return message length
+     */
+    public int getLength() {
+        return this.length;
+    }
+
+    /**
+     * Returns message version.
+     *
+     * @return message version
+     */
+    public byte getVersion() {
+        return this.version;
+    }
+
+    /**
+     * Returns message type.
+     *
+     * @return message type
+     */
+    public byte getType() {
+        return this.type;
+    }
+
+
+    @Override
+    public byte[] serialize() {
+        final byte[] data = new byte[DEFAULT_HEADER_LENGTH];
+        final ByteBuffer bb = ByteBuffer.wrap(data);
+
+        bb.put(this.version);
+        bb.put(this.type);
+        bb.putInt(this.length);
+
+        return data;
+    }
+
+
+    /**
+     * Deserializer function for Bmp Packets.
+     *
+     * @return deserializer function
+     */
+    public static Deserializer<Bmp> deserializer() {
+        return (data, offset, length) -> {
+            checkInput(data, offset, length, DEFAULT_HEADER_LENGTH);
+
+            ByteBuffer bb = ByteBuffer.wrap(data, offset, length);
+            Bmp bmp = new Bmp();
+
+            bmp.version = bb.get();
+            bmp.length = bb.getInt();
+            bmp.type = bb.get();
+
+            return bmp;
+        };
+    }
+
+    @Override
+    public String toString() {
+        return MoreObjects.toStringHelper(getClass())
+                .add("version", version)
+                .add("type", type)
+                .add("length", length)
+                .toString();
+    }
+}
+
diff --git a/utils/misc/src/main/java/org/onlab/packet/bmp/BmpPeer.java b/utils/misc/src/main/java/org/onlab/packet/bmp/BmpPeer.java
new file mode 100644
index 0000000..50c5dac
--- /dev/null
+++ b/utils/misc/src/main/java/org/onlab/packet/bmp/BmpPeer.java
@@ -0,0 +1,314 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.onlab.packet.bmp;
+
+import com.google.common.base.MoreObjects;
+import org.onlab.packet.BasePacket;
+import org.onlab.packet.Deserializer;
+import org.slf4j.Logger;
+
+import java.net.InetAddress;
+import java.net.UnknownHostException;
+import java.nio.ByteBuffer;
+
+import static org.onlab.packet.PacketUtils.checkInput;
+import static org.slf4j.LoggerFactory.getLogger;
+
+/**
+ * The per-peer header follows the common header for most BMP messages.
+ * The rest of the data in a BMP message is dependent on the Message
+ * Type field in the common header.
+ * <p>
+ * Peer Type (1 byte): Identifies the type of peer.  Currently, three
+ * types of peers are identified:
+ * <p>
+ * *  Peer Type = 0: Global Instance Peer
+ * *  Peer Type = 1: RD Instance Peer
+ * *  Peer Type = 2: Local Instance Peer
+ * <p>
+ * o  Peer Flags (1 byte): These flags provide more information about
+ * the peer.  The flags are defined as follows:
+ * <p>
+ * 0 1 2 3 4 5 6 7
+ * +-+-+-+-+-+-+-+-+
+ * |V|L|A| Reserved|
+ * +-+-+-+-+-+-+-+-+
+ * <p>
+ * *  The V flag indicates that the Peer address is an IPv6 address.
+ * For IPv4 peers, this is set to 0.
+ * <p>
+ * The L flag, if set to 1, indicates that the message reflects
+ * the post-policy Adj-RIB-In (i.e., its path attributes reflect
+ * the application of inbound policy).  It is set to 0 if the
+ * message reflects the pre-policy Adj-RIB-In.  Locally sourced
+ * routes also carry an L flag of 1.  See Section 5 for further
+ * detail.  This flag has no significance when used with route
+ * mirroring messages.
+ * <p>
+ * *  The A flag, if set to 1, indicates that the message is
+ * formatted using the legacy 2-byte AS_PATH format.  If set to 0,
+ * the message is formatted using the 4-byte AS_PATH format
+ * [RFC6793].  A BMP speaker MAY choose to propagate the AS_PATH
+ * information as received from its peer, or it MAY choose to
+ * reformat all AS_PATH information into a 4-byte format
+ * regardless of how it was received from the peer.  In the latter
+ * case, AS4_PATH or AS4_AGGREGATOR path attributes SHOULD NOT be
+ * sent in the BMP UPDATE message.  This flag has no significance
+ * when used with route mirroring messages.
+ * <p>
+ * The remaining bits are reserved for future use.  They MUST be
+ * transmitted as 0 and their values MUST be ignored on receipt.
+ * <p>
+ * Peer Distinguisher (8 bytes): Routers today can have multiple
+ * instances (example: Layer 3 Virtual Private Networks (L3VPNs)
+ * [RFC4364]).  This field is present to distinguish peers that
+ * belong to one address domain from the other.
+ * <p>
+ * If the peer is a "Global Instance Peer", this field is zero-
+ * filled.  If the peer is a "RD Instance Peer", it is set to the
+ * route distinguisher of the particular instance the peer belongs
+ * to.  If the peer is a "Local Instance Peer", it is set to a
+ * unique, locally defined value.  In all cases, the effect is that
+ * the combination of the Peer Type and Peer Distinguisher is
+ * sufficient to disambiguate peers for which other identifying
+ * information might overlap.
+ * <p>
+ * Peer Address: The remote IP address associated with the TCP
+ * session over which the encapsulated PDU was received.  It is 4
+ * bytes long if an IPv4 address is carried in this field (with the
+ * 12 most significant bytes zero-filled) and 16 bytes long if an
+ * IPv6 address is carried in this field.
+ * <p>
+ * Peer AS: The Autonomous System number of the peer from which the
+ * encapsulated PDU was received.  If a 16-bit AS number is stored in
+ * this field [RFC6793], it should be padded with zeroes in the 16
+ * most significant bits.
+ * <p>
+ * Timestamp: The time when the encapsulated routes were received
+ * (one may also think of this as the time when they were installed
+ * in the Adj-RIB-In), expressed in seconds and microseconds since
+ * midnight (zero hour), January 1, 1970 (UTC).  If zero, the time is
+ * unavailable.  Precision of the timestamp is implementation-
+ * dependent.
+ * <p>
+ * 4.3.  Initiation Message
+ * <p>
+ * The initiation message provides a means for the monitored router to
+ * inform the monitoring station of its vendor, software version, and so
+ * on.  An initiation message MUST be sent as the first message after
+ * the TCP session comes up.  An initiation message MAY be sent at any
+ * point thereafter, if warranted by a change on the monitored router.
+ * <p>
+ * The initiation message consists of the common BMP header followed by
+ * two or more Information TLVs containing information
+ * about the monitored router.  The sysDescr and sysName Information
+ * TLVs MUST be sent, any others are optional.  The string TLV MAY be
+ * included multiple times.
+ */
+public class BmpPeer extends BasePacket {
+
+    /*
+      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
+     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+     |   Peer Type   |  Peer Flags   |
+     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+     |         Peer Distinguisher (present based on peer type)       |
+     |                                                               |
+     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+     |                 Peer Address (16 bytes)                       |
+     ~                                                               ~
+     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+     |                           Peer AS                             |
+     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+     |                         Peer BGP ID                           |
+     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+     |                    Timestamp (seconds)                        |
+     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+     |                  Timestamp (microseconds)                     |
+     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+     */
+    public static final short PEER_HEADER_MINIMUM_LENGTH = 42;
+
+    public static final short PEER_DISTINGUISHER = 8;
+    public static final short IPV4_ADDRSZ = 4;
+    public static final short IPV6_ADDRSZ = 16;
+
+    protected byte type;
+
+    protected byte flags;
+
+    protected byte[] peerDistinguisher;
+
+    protected InetAddress peerAddress;
+
+    protected int peerAs;
+
+    protected int peerBgpId;
+
+    protected long seconds;
+
+    protected long microseconds;
+
+    private static Logger log = getLogger(BmpPeer.class);
+
+
+    /**
+     * Returns Peer Type.
+     *
+     * @return the peer type
+     */
+    public byte getType() {
+        return type;
+    }
+
+    /**
+     * Returns Peer Flag.
+     *
+     * @return the peer flag
+     */
+    public byte getFlag() {
+        return flags;
+    }
+
+    /**
+     * Returns Peer Distinguisher.
+     *
+     * @return the peer distingusiher
+     */
+    public byte[] getPeerDistinguisher() {
+        return peerDistinguisher;
+    }
+
+    /**
+     * Returns Peer IP Address.
+     *
+     * @return the peer ip address
+     */
+    public InetAddress getIntAddress() {
+        return peerAddress;
+    }
+
+    /**
+     * Returns Peer Autonomous System number.
+     *
+     * @return the peer AS number
+     */
+    public int getPeerAs() {
+        return peerAs;
+    }
+
+    /**
+     * Returns Peer Bgp Id.
+     *
+     * @return the bgp id
+     */
+    public int getPeerBgpId() {
+        return peerBgpId;
+    }
+
+    /**
+     * Returns timestamp in sec.
+     *
+     * @return the timestamp in sec
+     */
+    public long getSeconds() {
+        return seconds;
+    }
+
+    /**
+     * Returns timestamp in micro second.
+     *
+     * @return the timestamp in micro second
+     */
+    public long getMicroseconds() {
+        return microseconds;
+    }
+
+
+    @Override
+    public byte[] serialize() {
+        final byte[] data = new byte[PEER_HEADER_MINIMUM_LENGTH];
+        final ByteBuffer bb = ByteBuffer.wrap(data);
+
+        bb.put(this.type);
+        bb.put(this.flags);
+        bb.put(this.peerDistinguisher);
+        bb.put(this.peerAddress.getAddress());
+        bb.putInt(this.peerAs);
+        bb.putInt(this.peerBgpId);
+        bb.putLong(this.seconds);
+        bb.putLong(this.microseconds);
+
+        return data;
+    }
+
+    public static Deserializer<BmpPeer> deserializer() {
+        return (data, offset, length) -> {
+            checkInput(data, offset, length, PEER_HEADER_MINIMUM_LENGTH);
+
+            ByteBuffer bb = ByteBuffer.wrap(data, offset, length);
+            BmpPeer bmpPeer = new BmpPeer();
+
+            bmpPeer.type = bb.get();
+            bmpPeer.flags = bb.get();
+            bmpPeer.peerDistinguisher = new byte[PEER_DISTINGUISHER];
+            bb.get(bmpPeer.peerDistinguisher, 0, PEER_DISTINGUISHER);
+
+            if ((bmpPeer.flags & 0x80) != 0x00) {
+                bmpPeer.peerAddress = toInetAddress(IPV6_ADDRSZ, bb);
+            } else {
+                bb.position(bb.position() + (IPV6_ADDRSZ - IPV4_ADDRSZ));
+                bmpPeer.peerAddress = toInetAddress(IPV4_ADDRSZ, bb);
+            }
+
+            bmpPeer.peerAs = bb.getInt();
+            bmpPeer.peerBgpId = bb.getInt();
+            bmpPeer.seconds = bb.getInt();
+            bmpPeer.microseconds = bb.getInt();
+
+            return bmpPeer;
+        };
+    }
+
+    private static InetAddress toInetAddress(int length, ByteBuffer bb) {
+        byte[] address = new byte[length];
+        bb.get(address, 0, length);
+        InetAddress ipAddress = null;
+        try {
+            ipAddress = InetAddress.getByAddress(address);
+        } catch (UnknownHostException e) {
+            log.error("InetAddress conversion failed");
+        }
+
+        return ipAddress;
+    }
+
+    @Override
+    public String toString() {
+
+        return MoreObjects.toStringHelper(getClass())
+                .add("flags", flags)
+                .add("type", type)
+                .add("peerAddress", peerAddress.getHostAddress())
+                .add("peerAs", peerAs)
+                .add("seconds", seconds)
+                .add("microseconds", microseconds)
+                .toString();
+    }
+
+}
diff --git a/utils/misc/src/main/java/org/onlab/packet/bmp/package-info.java b/utils/misc/src/main/java/org/onlab/packet/bmp/package-info.java
new file mode 100644
index 0000000..ea8cb4a
--- /dev/null
+++ b/utils/misc/src/main/java/org/onlab/packet/bmp/package-info.java
@@ -0,0 +1,19 @@
+/*
+ * Copyright 2021-present Open Networking Foundation
+ *
+ * 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.
+ */
+/**
+ * Utility for decoding bmp options.
+ */
+package org.onlab.packet.bmp;
\ No newline at end of file