Add support for timing out idle FPM connections.

This requires support for sending keepalives on the Quagga side.

Change-Id: I8551eb17b51460f2a66a7086b5c8006cc0d214a5
diff --git a/apps/routing/fpm/src/main/java/org/onosproject/routing/fpm/protocol/FpmHeader.java b/apps/routing/fpm/src/main/java/org/onosproject/routing/fpm/protocol/FpmHeader.java
index 5bba9fb..85ee9bc 100644
--- a/apps/routing/fpm/src/main/java/org/onosproject/routing/fpm/protocol/FpmHeader.java
+++ b/apps/routing/fpm/src/main/java/org/onosproject/routing/fpm/protocol/FpmHeader.java
@@ -17,6 +17,7 @@
 package org.onosproject.routing.fpm.protocol;
 
 import com.google.common.base.MoreObjects;
+import com.google.common.collect.ImmutableSet;
 import org.onlab.packet.DeserializationException;
 
 import java.nio.ByteBuffer;
@@ -30,7 +31,17 @@
     public static final int FPM_HEADER_LENGTH = 4;
 
     public static final short FPM_VERSION_1 = 1;
+    public static final short FPM_VERSION_ONOS_EXT = 32;
+
+    private static final ImmutableSet<Short> SUPPORTED_VERSIONS =
+            ImmutableSet.<Short>builder()
+            .add(FPM_VERSION_1)
+            .add(FPM_VERSION_ONOS_EXT)
+            .build();
+
     public static final short FPM_TYPE_NETLINK = 1;
+    public static final short FPM_TYPE_PROTOBUF = 2;
+    public static final short FPM_TYPE_KEEPALIVE = 32;
 
     private static final String VERSION_NOT_SUPPORTED = "FPM version not supported: ";
     private static final String TYPE_NOT_SUPPORTED = "FPM type not supported: ";
@@ -119,17 +130,21 @@
         ByteBuffer bb = ByteBuffer.wrap(buffer, start, length);
 
         short version = bb.get();
-        if (version != FPM_VERSION_1) {
+        if (!SUPPORTED_VERSIONS.contains(version)) {
             throw new DeserializationException(VERSION_NOT_SUPPORTED + version);
         }
 
         short type = bb.get();
+        int messageLength = bb.getShort();
+
+        if (type == FPM_TYPE_KEEPALIVE) {
+            return new FpmHeader(version, type, messageLength, null);
+        }
+
         if (type != FPM_TYPE_NETLINK) {
             throw new DeserializationException(TYPE_NOT_SUPPORTED + type);
         }
 
-        int messageLength = bb.getShort();
-
         Netlink netlink = Netlink.decode(buffer, bb.position(), bb.limit() - bb.position());
 
         return new FpmHeader(version, type, messageLength, netlink);