diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/AreaId.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/AreaId.java
index 79a326d..f3c3b5d 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/AreaId.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/AreaId.java
@@ -1,70 +1,70 @@
-/*
- * 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.iptopology.api;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-
-import java.util.Objects;
-
-/**
- * Area identifier class (32 Bit Area-ID).
- */
-public class AreaId {
-    private final int areaId;
-
-    /**
-     * Constructor to set area identifier.
-     *
-     * @param areaId area id
-     */
-    public AreaId(int areaId) {
-        this.areaId = areaId;
-    }
-
-    /**
-     * obtain area identifier.
-     *
-     * @return area identifier
-     */
-    public int areaId() {
-        return areaId;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(areaId);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-
-        if (obj instanceof AreaId) {
-            AreaId other = (AreaId) obj;
-            return Objects.equals(areaId, other.areaId);
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .add("areaId", areaId)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+
+import java.util.Objects;
+
+/**
+ * Area identifier class (32 Bit Area-ID).
+ */
+public class AreaId {
+    private final int areaId;
+
+    /**
+     * Constructor to set area identifier.
+     *
+     * @param areaId area id
+     */
+    public AreaId(int areaId) {
+        this.areaId = areaId;
+    }
+
+    /**
+     * obtain area identifier.
+     *
+     * @return area identifier
+     */
+    public int areaId() {
+        return areaId;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(areaId);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+
+        if (obj instanceof AreaId) {
+            AreaId other = (AreaId) obj;
+            return Objects.equals(areaId, other.areaId);
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .add("areaId", areaId)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/AsNumber.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/AsNumber.java
index 3159b20..34b04c2 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/AsNumber.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/AsNumber.java
@@ -1,70 +1,70 @@
-/*
- * 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.iptopology.api;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-
-import java.util.Objects;
-
-/**
- * Autonomous system Number class (32 Bit ASNumber).
- */
-public class AsNumber {
-    private final int asNum;
-
-    /**
-     * Constructor to set As number.
-     *
-     * @param asNum As number
-     */
-    public AsNumber(int asNum) {
-        this.asNum = asNum;
-    }
-
-    /**
-     * Obtain autonomous system number.
-     *
-     * @return autonomous system number
-     */
-    public int asNum() {
-        return asNum;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(asNum);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-
-        if (obj instanceof AsNumber) {
-            AsNumber other = (AsNumber) obj;
-            return Objects.equals(asNum, other.asNum);
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .add("asNum", asNum)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+
+import java.util.Objects;
+
+/**
+ * Autonomous system Number class (32 Bit ASNumber).
+ */
+public class AsNumber {
+    private final int asNum;
+
+    /**
+     * Constructor to set As number.
+     *
+     * @param asNum As number
+     */
+    public AsNumber(int asNum) {
+        this.asNum = asNum;
+    }
+
+    /**
+     * Obtain autonomous system number.
+     *
+     * @return autonomous system number
+     */
+    public int asNum() {
+        return asNum;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(asNum);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+
+        if (obj instanceof AsNumber) {
+            AsNumber other = (AsNumber) obj;
+            return Objects.equals(asNum, other.asNum);
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .add("asNum", asNum)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultDeviceIntf.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultDeviceIntf.java
index e40cbfc..292fce0 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultDeviceIntf.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultDeviceIntf.java
@@ -1,79 +1,79 @@
-/*
- * 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.iptopology.api;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-
-import java.util.Objects;
-
-import org.onosproject.net.Element;
-
-/**
- * Default Device interface implementation.
- */
-public class DefaultDeviceIntf implements DeviceIntf {
-
-    private final Element element;
-    private final DeviceInterface deviceInterface;
-
-    /**
-     * Constructor to initialize device interface parameters.
-     *
-     * @param element parent network element
-     * @param deviceInterface device interface
-     */
-    public DefaultDeviceIntf(Element element, DeviceInterface deviceInterface) {
-        this.element = element;
-        this.deviceInterface = deviceInterface;
-    }
-
-    @Override
-    public Element element() {
-        return element;
-    }
-
-    @Override
-    public DeviceInterface deviceInterface() {
-        return deviceInterface;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(element, deviceInterface);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-
-        if (obj instanceof DefaultDeviceIntf) {
-            final DefaultDeviceIntf other = (DefaultDeviceIntf) obj;
-            return Objects.equals(this.element.id(), other.element.id())
-                    && Objects.equals(this.deviceInterface, other.deviceInterface);
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .add("element", element.id())
-                .add("deviceInterface", deviceInterface)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+
+import java.util.Objects;
+
+import org.onosproject.net.Element;
+
+/**
+ * Default Device interface implementation.
+ */
+public class DefaultDeviceIntf implements DeviceIntf {
+
+    private final Element element;
+    private final DeviceInterface deviceInterface;
+
+    /**
+     * Constructor to initialize device interface parameters.
+     *
+     * @param element parent network element
+     * @param deviceInterface device interface
+     */
+    public DefaultDeviceIntf(Element element, DeviceInterface deviceInterface) {
+        this.element = element;
+        this.deviceInterface = deviceInterface;
+    }
+
+    @Override
+    public Element element() {
+        return element;
+    }
+
+    @Override
+    public DeviceInterface deviceInterface() {
+        return deviceInterface;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(element, deviceInterface);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+
+        if (obj instanceof DefaultDeviceIntf) {
+            final DefaultDeviceIntf other = (DefaultDeviceIntf) obj;
+            return Objects.equals(this.element.id(), other.element.id())
+                    && Objects.equals(this.deviceInterface, other.deviceInterface);
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .add("element", element.id())
+                .add("deviceInterface", deviceInterface)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultDevicePrefix.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultDevicePrefix.java
index 2b1dde6..6392c1d 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultDevicePrefix.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultDevicePrefix.java
@@ -1,95 +1,95 @@
-/*
- * 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.iptopology.api;
-
-import org.onosproject.net.AbstractAnnotated;
-import org.onosproject.net.Annotations;
-import org.onosproject.net.Element;
-
-import java.util.Objects;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-
-/**
- * Default Device prefix implementation.
- */
-public class DefaultDevicePrefix extends AbstractAnnotated implements DevicePrefix {
-
-    private final Element element;
-    private final PrefixIdentifier prefixIdentifier;
-    private final PrefixTed prefixTed;
-
-    /**
-     * Creates a network device prefix attributed to the specified element.
-     *
-     * @param element           parent network element
-     * @param prefixIdentifier  prefix identifier
-     * @param prefixTed         prefid traffic engineering parameters
-     * @param annotations       optional key/value annotations
-     */
-    public DefaultDevicePrefix(Element element, PrefixIdentifier prefixIdentifier,
-                               PrefixTed prefixTed, Annotations... annotations) {
-        super(annotations);
-        this.element = element;
-        this.prefixIdentifier = prefixIdentifier;
-        this.prefixTed = prefixTed;
-    }
-
-    @Override
-    public Element element() {
-        return element;
-    }
-
-    @Override
-    public PrefixIdentifier prefixIdentifier() {
-        return prefixIdentifier;
-    }
-
-    @Override
-    public PrefixTed prefixTed() {
-        return prefixTed;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(element, prefixIdentifier, prefixTed);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-        if (obj instanceof DefaultDevicePrefix) {
-            final DefaultDevicePrefix other = (DefaultDevicePrefix) obj;
-            return Objects.equals(this.element.id(), other.element.id()) &&
-                    Objects.equals(this.prefixIdentifier, other.prefixIdentifier) &&
-                    Objects.equals(this.prefixTed, other.prefixTed) &&
-                    Objects.equals(this.annotations(), other.annotations());
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .omitNullValues()
-                .add("element", element.id())
-                .add("prefixIdentifier", prefixIdentifier)
-                .add("prefixTed", prefixTed)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import org.onosproject.net.AbstractAnnotated;
+import org.onosproject.net.Annotations;
+import org.onosproject.net.Element;
+
+import java.util.Objects;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+
+/**
+ * Default Device prefix implementation.
+ */
+public class DefaultDevicePrefix extends AbstractAnnotated implements DevicePrefix {
+
+    private final Element element;
+    private final PrefixIdentifier prefixIdentifier;
+    private final PrefixTed prefixTed;
+
+    /**
+     * Creates a network device prefix attributed to the specified element.
+     *
+     * @param element           parent network element
+     * @param prefixIdentifier  prefix identifier
+     * @param prefixTed         prefid traffic engineering parameters
+     * @param annotations       optional key/value annotations
+     */
+    public DefaultDevicePrefix(Element element, PrefixIdentifier prefixIdentifier,
+                               PrefixTed prefixTed, Annotations... annotations) {
+        super(annotations);
+        this.element = element;
+        this.prefixIdentifier = prefixIdentifier;
+        this.prefixTed = prefixTed;
+    }
+
+    @Override
+    public Element element() {
+        return element;
+    }
+
+    @Override
+    public PrefixIdentifier prefixIdentifier() {
+        return prefixIdentifier;
+    }
+
+    @Override
+    public PrefixTed prefixTed() {
+        return prefixTed;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(element, prefixIdentifier, prefixTed);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+        if (obj instanceof DefaultDevicePrefix) {
+            final DefaultDevicePrefix other = (DefaultDevicePrefix) obj;
+            return Objects.equals(this.element.id(), other.element.id()) &&
+                    Objects.equals(this.prefixIdentifier, other.prefixIdentifier) &&
+                    Objects.equals(this.prefixTed, other.prefixTed) &&
+                    Objects.equals(this.annotations(), other.annotations());
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .omitNullValues()
+                .add("element", element.id())
+                .add("prefixIdentifier", prefixIdentifier)
+                .add("prefixTed", prefixTed)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultIpDevice.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultIpDevice.java
index a2d0165..56bca45 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultIpDevice.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultIpDevice.java
@@ -1,113 +1,113 @@
-/*
- * 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.iptopology.api;
-
-import org.onosproject.net.AbstractElement;
-import org.onosproject.net.Annotations;
-import org.onosproject.net.DeviceId;
-import org.onosproject.net.provider.ProviderId;
-
-import java.util.Objects;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-
-/**
- * Default ip device model implementation.
- */
-public class DefaultIpDevice extends AbstractElement implements IpDevice {
-
-    private final Type type;
-    private final IpDeviceIdentifier deviceIdentifier;
-    private final DeviceTed deviceTed;
-
-
-    /**
-     * For Serialization.
-     */
-    private DefaultIpDevice() {
-        this.type = null;
-        this.deviceIdentifier = null;
-        this.deviceTed = null;
-    }
-
-    /**
-     * Creates a network element attributed to the specified provider.
-     *
-     * @param providerId   identity of the provider
-     * @param id           device identifier
-     * @param type         device type
-     * @param deviceIdentifier provides device identifier details
-     * @param deviceTed device traffic engineering parameters
-     * @param annotations  optional key/value annotations
-     */
-    public DefaultIpDevice(ProviderId providerId, DeviceId id, Type type,
-                         IpDeviceIdentifier deviceIdentifier, DeviceTed deviceTed,
-                         Annotations... annotations) {
-        super(providerId, id, annotations);
-        this.type = type;
-        this.deviceIdentifier = deviceIdentifier;
-        this.deviceTed = deviceTed;
-    }
-
-    @Override
-    public DeviceId id() {
-        return (DeviceId) id;
-    }
-
-    @Override
-    public Type type() {
-        return type;
-    }
-
-    @Override
-    public IpDeviceIdentifier deviceIdentifier() {
-        return deviceIdentifier;
-    }
-
-    @Override
-    public DeviceTed deviceTed() {
-        return deviceTed; }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(type, deviceIdentifier, deviceTed);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-
-        if (obj instanceof DefaultIpDevice) {
-            final DefaultIpDevice other = (DefaultIpDevice) obj;
-            return Objects.equals(this.id, other.id) &&
-                    Objects.equals(this.type, other.type) &&
-                    Objects.equals(this.deviceIdentifier, other.deviceIdentifier) &&
-                    Objects.equals(this.deviceTed, other.deviceTed);
-        }
-        return false;
-    }
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .omitNullValues()
-                .add("id", id)
-                .add("deviceIdentifier", deviceIdentifier)
-                .add("deviceTed", deviceTed)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import org.onosproject.net.AbstractElement;
+import org.onosproject.net.Annotations;
+import org.onosproject.net.DeviceId;
+import org.onosproject.net.provider.ProviderId;
+
+import java.util.Objects;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+
+/**
+ * Default ip device model implementation.
+ */
+public class DefaultIpDevice extends AbstractElement implements IpDevice {
+
+    private final Type type;
+    private final IpDeviceIdentifier deviceIdentifier;
+    private final DeviceTed deviceTed;
+
+
+    /**
+     * For Serialization.
+     */
+    private DefaultIpDevice() {
+        this.type = null;
+        this.deviceIdentifier = null;
+        this.deviceTed = null;
+    }
+
+    /**
+     * Creates a network element attributed to the specified provider.
+     *
+     * @param providerId   identity of the provider
+     * @param id           device identifier
+     * @param type         device type
+     * @param deviceIdentifier provides device identifier details
+     * @param deviceTed device traffic engineering parameters
+     * @param annotations  optional key/value annotations
+     */
+    public DefaultIpDevice(ProviderId providerId, DeviceId id, Type type,
+                         IpDeviceIdentifier deviceIdentifier, DeviceTed deviceTed,
+                         Annotations... annotations) {
+        super(providerId, id, annotations);
+        this.type = type;
+        this.deviceIdentifier = deviceIdentifier;
+        this.deviceTed = deviceTed;
+    }
+
+    @Override
+    public DeviceId id() {
+        return (DeviceId) id;
+    }
+
+    @Override
+    public Type type() {
+        return type;
+    }
+
+    @Override
+    public IpDeviceIdentifier deviceIdentifier() {
+        return deviceIdentifier;
+    }
+
+    @Override
+    public DeviceTed deviceTed() {
+        return deviceTed; }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(type, deviceIdentifier, deviceTed);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+
+        if (obj instanceof DefaultIpDevice) {
+            final DefaultIpDevice other = (DefaultIpDevice) obj;
+            return Objects.equals(this.id, other.id) &&
+                    Objects.equals(this.type, other.type) &&
+                    Objects.equals(this.deviceIdentifier, other.deviceIdentifier) &&
+                    Objects.equals(this.deviceTed, other.deviceTed);
+        }
+        return false;
+    }
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .omitNullValues()
+                .add("id", id)
+                .add("deviceIdentifier", deviceIdentifier)
+                .add("deviceTed", deviceTed)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultIpLink.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultIpLink.java
index 4767074..d8c8425 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultIpLink.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DefaultIpLink.java
@@ -1,106 +1,106 @@
-/*
- * 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.iptopology.api;
-
-import org.onosproject.net.AbstractModel;
-import org.onosproject.net.Annotations;
-import org.onosproject.net.provider.ProviderId;
-
-import java.util.Objects;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-
-/**
- * This class provides Link identifier and link ted details.
- */
-public class DefaultIpLink extends AbstractModel implements IpLink {
-
-    private final TerminationPoint src;
-    private final TerminationPoint dst;
-    private final IpLinkIdentifier linkIdentifier;
-    private final LinkTed linkTed;
-
-    /**
-     * Constructor to initialize its parameters.
-     *
-     * @param providerId     provider identification
-     * @param src            link source termination point
-     * @param dst            link destination termination point
-     * @param linkIdentifier provides link identifier details
-     * @param linkTed        provides link traffic engineering details
-     * @param annotations    optional key/value annotations
-     */
-    public DefaultIpLink(ProviderId providerId, TerminationPoint src, TerminationPoint dst,
-                         IpLinkIdentifier linkIdentifier, LinkTed linkTed,
-                         Annotations... annotations) {
-        super(providerId, annotations);
-        this.src = src;
-        this.dst = dst;
-        this.linkIdentifier = linkIdentifier;
-        this.linkTed = linkTed;
-    }
-
-    @Override
-    public TerminationPoint src() {
-        return src;
-    }
-
-    @Override
-    public TerminationPoint dst() {
-        return dst;
-    }
-
-    @Override
-    public IpLinkIdentifier linkIdentifier() {
-        return linkIdentifier;
-    }
-
-    @Override
-    public LinkTed linkTed() {
-        return linkTed;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(src, dst, linkIdentifier, linkTed);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-        if (obj instanceof DefaultIpLink) {
-            final DefaultIpLink other = (DefaultIpLink) obj;
-            return Objects.equals(this.src, other.src) &&
-                    Objects.equals(this.dst, other.dst) &&
-                    Objects.equals(this.linkIdentifier, other.linkIdentifier) &&
-                    Objects.equals(this.linkTed, other.linkTed);
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .omitNullValues()
-                .add("src", src)
-                .add("dst", dst)
-                .add("linkIdentifier", linkIdentifier)
-                .add("linkTed", linkTed)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import org.onosproject.net.AbstractModel;
+import org.onosproject.net.Annotations;
+import org.onosproject.net.provider.ProviderId;
+
+import java.util.Objects;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+
+/**
+ * This class provides Link identifier and link ted details.
+ */
+public class DefaultIpLink extends AbstractModel implements IpLink {
+
+    private final TerminationPoint src;
+    private final TerminationPoint dst;
+    private final IpLinkIdentifier linkIdentifier;
+    private final LinkTed linkTed;
+
+    /**
+     * Constructor to initialize its parameters.
+     *
+     * @param providerId     provider identification
+     * @param src            link source termination point
+     * @param dst            link destination termination point
+     * @param linkIdentifier provides link identifier details
+     * @param linkTed        provides link traffic engineering details
+     * @param annotations    optional key/value annotations
+     */
+    public DefaultIpLink(ProviderId providerId, TerminationPoint src, TerminationPoint dst,
+                         IpLinkIdentifier linkIdentifier, LinkTed linkTed,
+                         Annotations... annotations) {
+        super(providerId, annotations);
+        this.src = src;
+        this.dst = dst;
+        this.linkIdentifier = linkIdentifier;
+        this.linkTed = linkTed;
+    }
+
+    @Override
+    public TerminationPoint src() {
+        return src;
+    }
+
+    @Override
+    public TerminationPoint dst() {
+        return dst;
+    }
+
+    @Override
+    public IpLinkIdentifier linkIdentifier() {
+        return linkIdentifier;
+    }
+
+    @Override
+    public LinkTed linkTed() {
+        return linkTed;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(src, dst, linkIdentifier, linkTed);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+        if (obj instanceof DefaultIpLink) {
+            final DefaultIpLink other = (DefaultIpLink) obj;
+            return Objects.equals(this.src, other.src) &&
+                    Objects.equals(this.dst, other.dst) &&
+                    Objects.equals(this.linkIdentifier, other.linkIdentifier) &&
+                    Objects.equals(this.linkTed, other.linkTed);
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .omitNullValues()
+                .add("src", src)
+                .add("dst", dst)
+                .add("linkIdentifier", linkIdentifier)
+                .add("linkTed", linkTed)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DeviceInterface.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DeviceInterface.java
index 131aa62..3a16ec4 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DeviceInterface.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DeviceInterface.java
@@ -1,100 +1,100 @@
-/*
- * 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.iptopology.api;
-
-import java.util.Objects;
-
-import org.onlab.packet.Ip4Address;
-import org.onlab.packet.Ip6Address;
-
-import com.google.common.base.MoreObjects;
-
-/**
- * Representation of device interface.
- */
-public class DeviceInterface {
-    private final Ip4Address ip4Address;
-    private final Ip6Address ip6Address;
-    private final InterfaceIdentifier interfaceId;
-
-    /**
-     * Constructor to initialize its parameter.
-     *
-     * @param ip4Address ipv4 interface address
-     * @param ip6Address ipv6 interface address
-     * @param interfaceId interface Identifier
-     */
-    public DeviceInterface(Ip4Address ip4Address, Ip6Address ip6Address, InterfaceIdentifier interfaceId) {
-        this.ip4Address = ip4Address;
-        this.ip6Address = ip6Address;
-        this.interfaceId = interfaceId;
-    }
-
-    /**
-     * obtains ipv4 address of an interface.
-     *
-     * @return ipv4 interface address
-     */
-    public Ip4Address ip4Address() {
-        return ip4Address;
-    }
-
-    /**
-     * obtains ipv6 interface address.
-     *
-     * @return ipv6 interface address
-     */
-    public Ip6Address ip6Address() {
-        return ip6Address;
-    }
-
-    /**
-     * obtains interface identifier.
-     *
-     * @return interface identifier
-     */
-    public InterfaceIdentifier interfaceId() {
-        return interfaceId;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(ip4Address, ip6Address, interfaceId);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-        if (obj instanceof DeviceInterface) {
-            final DeviceInterface other = (DeviceInterface) obj;
-            return Objects.equals(this.ip4Address, other.ip4Address)
-                    && Objects.equals(this.ip6Address, other.ip6Address)
-                    && Objects.equals(this.interfaceId, other.interfaceId);
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(this)
-                .add("ip4Address", ip4Address)
-                .add("ip6Address", ip6Address)
-                .add("interfaceId", interfaceId)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import java.util.Objects;
+
+import org.onlab.packet.Ip4Address;
+import org.onlab.packet.Ip6Address;
+
+import com.google.common.base.MoreObjects;
+
+/**
+ * Representation of device interface.
+ */
+public class DeviceInterface {
+    private final Ip4Address ip4Address;
+    private final Ip6Address ip6Address;
+    private final InterfaceIdentifier interfaceId;
+
+    /**
+     * Constructor to initialize its parameter.
+     *
+     * @param ip4Address ipv4 interface address
+     * @param ip6Address ipv6 interface address
+     * @param interfaceId interface Identifier
+     */
+    public DeviceInterface(Ip4Address ip4Address, Ip6Address ip6Address, InterfaceIdentifier interfaceId) {
+        this.ip4Address = ip4Address;
+        this.ip6Address = ip6Address;
+        this.interfaceId = interfaceId;
+    }
+
+    /**
+     * obtains ipv4 address of an interface.
+     *
+     * @return ipv4 interface address
+     */
+    public Ip4Address ip4Address() {
+        return ip4Address;
+    }
+
+    /**
+     * obtains ipv6 interface address.
+     *
+     * @return ipv6 interface address
+     */
+    public Ip6Address ip6Address() {
+        return ip6Address;
+    }
+
+    /**
+     * obtains interface identifier.
+     *
+     * @return interface identifier
+     */
+    public InterfaceIdentifier interfaceId() {
+        return interfaceId;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(ip4Address, ip6Address, interfaceId);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+        if (obj instanceof DeviceInterface) {
+            final DeviceInterface other = (DeviceInterface) obj;
+            return Objects.equals(this.ip4Address, other.ip4Address)
+                    && Objects.equals(this.ip6Address, other.ip6Address)
+                    && Objects.equals(this.interfaceId, other.interfaceId);
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return MoreObjects.toStringHelper(this)
+                .add("ip4Address", ip4Address)
+                .add("ip6Address", ip6Address)
+                .add("interfaceId", interfaceId)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DeviceIntf.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DeviceIntf.java
index ff18d3a..e25f041 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DeviceIntf.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DeviceIntf.java
@@ -1,37 +1,37 @@
-/*
- * 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.iptopology.api;
-
-import org.onosproject.net.Element;
-
-/**
- * Abstraction of Device interface.
- */
-public interface DeviceIntf {
-    /**
-     * Returns the parent network element to which this interface belongs.
-     *
-     * @return parent network element
-     */
-    Element element();
-
-    /**
-     * Returns device interface details.
-     *
-     * @return device interface details
-     */
-    DeviceInterface deviceInterface();
+/*
+ * 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.iptopology.api;
+
+import org.onosproject.net.Element;
+
+/**
+ * Abstraction of Device interface.
+ */
+public interface DeviceIntf {
+    /**
+     * Returns the parent network element to which this interface belongs.
+     *
+     * @return parent network element
+     */
+    Element element();
+
+    /**
+     * Returns device interface details.
+     *
+     * @return device interface details
+     */
+    DeviceInterface deviceInterface();
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DevicePrefix.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DevicePrefix.java
index 89efccd..928c7eb 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DevicePrefix.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DevicePrefix.java
@@ -1,46 +1,46 @@
-/*
- * 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.iptopology.api;
-
-import org.onosproject.net.Annotated;
-import org.onosproject.net.Element;
-
-/**
- * Abstraction of Device Prefix.
- */
-public interface DevicePrefix extends Annotated {
-
-    /**
-     * Returns the parent network element to which this port belongs.
-     *
-     * @return parent network element
-     */
-    Element element();
-
-    /**
-     * Returns prefix identifier details.
-     *
-     *  @return prefix identifier details
-     */
-    PrefixIdentifier prefixIdentifier();
-
-    /**
-     * Returns prefix Traffic engineering parameters.
-     *
-     * @return prefix Traffic engineering parameters
-     */
-    PrefixTed prefixTed();
+/*
+ * 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.iptopology.api;
+
+import org.onosproject.net.Annotated;
+import org.onosproject.net.Element;
+
+/**
+ * Abstraction of Device Prefix.
+ */
+public interface DevicePrefix extends Annotated {
+
+    /**
+     * Returns the parent network element to which this port belongs.
+     *
+     * @return parent network element
+     */
+    Element element();
+
+    /**
+     * Returns prefix identifier details.
+     *
+     *  @return prefix identifier details
+     */
+    PrefixIdentifier prefixIdentifier();
+
+    /**
+     * Returns prefix Traffic engineering parameters.
+     *
+     * @return prefix Traffic engineering parameters
+     */
+    PrefixTed prefixTed();
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DomainId.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DomainId.java
index 4fb1070..6d94bc2 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DomainId.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/DomainId.java
@@ -1,71 +1,71 @@
-/*
- * 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.iptopology.api;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-
-import java.util.Objects;
-
-/**
- * Domain Identifier(32 Bit).
- */
-public class DomainId {
-    private final int domainIdentifier;
-
-    /**
-     * Constructor to initialize domain identifier.
-     *
-     * @param domainIdentifier domain identifier
-     */
-    public DomainId(int domainIdentifier) {
-        this.domainIdentifier = domainIdentifier;
-    }
-
-    /**
-     * Obtain domain identifier.
-     *
-     * @return domain identifier
-     */
-    public int domainIdentifier() {
-        return domainIdentifier;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(domainIdentifier);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-
-        if (obj instanceof DomainId) {
-            DomainId other = (DomainId) obj;
-            return Objects.equals(domainIdentifier, other.domainIdentifier);
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .add("domainIdentifier", domainIdentifier)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+
+import java.util.Objects;
+
+/**
+ * Domain Identifier(32 Bit).
+ */
+public class DomainId {
+    private final int domainIdentifier;
+
+    /**
+     * Constructor to initialize domain identifier.
+     *
+     * @param domainIdentifier domain identifier
+     */
+    public DomainId(int domainIdentifier) {
+        this.domainIdentifier = domainIdentifier;
+    }
+
+    /**
+     * Obtain domain identifier.
+     *
+     * @return domain identifier
+     */
+    public int domainIdentifier() {
+        return domainIdentifier;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(domainIdentifier);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+
+        if (obj instanceof DomainId) {
+            DomainId other = (DomainId) obj;
+            return Objects.equals(domainIdentifier, other.domainIdentifier);
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .add("domainIdentifier", domainIdentifier)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpDevice.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpDevice.java
index 131b7ea..440841f 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpDevice.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpDevice.java
@@ -1,68 +1,68 @@
-/*
- * 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.iptopology.api;
-
-import org.onosproject.net.DeviceId;
-import org.onosproject.net.Element;
-
-/**
- * Abstraction of Ip Device.
- */
-public interface IpDevice extends Element {
-    /**
-     ** Enum type to store Device Type.
-     */
-    enum Type {
-        /**
-         * Signifies that the device is pseudo device.
-         */
-        PSEUDO,
-
-        /**
-         * Signifies that the device is non-pseudo device.
-         */
-        NONPSEUDO;
-    }
-
-    /**
-     * Obtains device id.
-     *
-     * @return device id
-     */
-    @Override
-    DeviceId id();
-
-    /**
-     * Obtains device type.
-     *
-     * @return device type
-     */
-    Type type();
-
-    /**
-     * Obtains Device identifier details.
-     *
-     * @return identifier of the device
-     */
-    IpDeviceIdentifier deviceIdentifier();
-
-    /**
-     * Obtains the traffic engineering parameters of the device.
-     *
-     * @return traffic engineering parameters of the device
-     */
-    DeviceTed deviceTed();
+/*
+ * 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.iptopology.api;
+
+import org.onosproject.net.DeviceId;
+import org.onosproject.net.Element;
+
+/**
+ * Abstraction of Ip Device.
+ */
+public interface IpDevice extends Element {
+    /**
+     ** Enum type to store Device Type.
+     */
+    enum Type {
+        /**
+         * Signifies that the device is pseudo device.
+         */
+        PSEUDO,
+
+        /**
+         * Signifies that the device is non-pseudo device.
+         */
+        NONPSEUDO;
+    }
+
+    /**
+     * Obtains device id.
+     *
+     * @return device id
+     */
+    @Override
+    DeviceId id();
+
+    /**
+     * Obtains device type.
+     *
+     * @return device type
+     */
+    Type type();
+
+    /**
+     * Obtains Device identifier details.
+     *
+     * @return identifier of the device
+     */
+    IpDeviceIdentifier deviceIdentifier();
+
+    /**
+     * Obtains the traffic engineering parameters of the device.
+     *
+     * @return traffic engineering parameters of the device
+     */
+    DeviceTed deviceTed();
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpDeviceIdentifier.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpDeviceIdentifier.java
index 7be13ad..295d799 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpDeviceIdentifier.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpDeviceIdentifier.java
@@ -1,142 +1,142 @@
-/*
- * 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.iptopology.api;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-
-import java.util.Objects;
-
-/**
- * Represents IP Device Identifiers.
- */
-public class IpDeviceIdentifier {
-
-    private final RouteDistinguisher routeDish;
-    private final RouteInstance routeInstance;
-    private final AsNumber asNum;
-    private final DomainId domainIdentifier;
-    private final AreaId areaId;
-    private final RouteIdentifier routerIdentifier;
-
-    /**
-     * Constructor to initialize parameters.
-     *
-     * @param routeDish routing distinguisher instance
-     * @param routeInstance routing protocol instance
-     * @param asNum AS number
-     * @param domainIdentifier BGP-LS domain
-     * @param areaId Area ID
-     * @param routerIdentifier IGP router ID
-     */
-    public IpDeviceIdentifier(RouteDistinguisher routeDish, RouteInstance routeInstance, AsNumber asNum,
-                           DomainId domainIdentifier, AreaId areaId, RouteIdentifier routerIdentifier) {
-        this.routeDish = routeDish;
-        this.areaId = areaId;
-        this.asNum = asNum;
-        this.domainIdentifier = domainIdentifier;
-        this.routeInstance = routeInstance;
-        this.routerIdentifier = routerIdentifier;
-    }
-
-    /**
-     * Obtains Route Distinguisher of Ip Device.
-     *
-     * @return Area ID
-     */
-    public RouteDistinguisher routeDish() {
-        return routeDish;
-    }
-
-    /**
-     * Obtains Area ID if Ip Device.
-     *
-     * @return Area ID
-     */
-    public AreaId areaId() {
-        return areaId;
-    }
-
-    /**
-     * Obtains AS number of Ip Device.
-     *
-     * @return AS number
-     */
-    public AsNumber asNum() {
-        return asNum;
-    }
-
-    /**
-     * Obtains domain identifier of Ip Device.
-     *
-     * @return domain identifier
-     */
-    public DomainId domainIdentifier() {
-        return domainIdentifier;
-    }
-
-    /**
-     * Obtains Router id of Ip Device.
-     *
-     * @return Router id
-     */
-    public RouteIdentifier routerIdentifier() {
-        return routerIdentifier;
-    }
-
-    /**
-     * Obtains routing protocol instance.
-     *
-     * @return routing protocol instance
-     */
-    public RouteInstance routeInstance() {
-        return routeInstance;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(routeDish, areaId, asNum, domainIdentifier, routerIdentifier, routeInstance);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-
-        if (obj instanceof IpDeviceIdentifier) {
-            IpDeviceIdentifier other = (IpDeviceIdentifier) obj;
-            return Objects.equals(areaId, other.areaId) && Objects.equals(asNum, other.asNum)
-                    && Objects.equals(domainIdentifier, other.domainIdentifier)
-                    && Objects.equals(routerIdentifier, other.routerIdentifier)
-                    && Objects.equals(routeInstance, other.routeInstance)
-                    && Objects.equals(routeDish, other.routeDish);
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .omitNullValues()
-                .add("areaId", areaId)
-                .add("asNum", asNum)
-                .add("domainIdentifier", domainIdentifier)
-                .add("routerIdentifier", routerIdentifier)
-                .add("routeInstance", routeInstance)
-                .add("routeDish", routeDish)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+
+import java.util.Objects;
+
+/**
+ * Represents IP Device Identifiers.
+ */
+public class IpDeviceIdentifier {
+
+    private final RouteDistinguisher routeDish;
+    private final RouteInstance routeInstance;
+    private final AsNumber asNum;
+    private final DomainId domainIdentifier;
+    private final AreaId areaId;
+    private final RouteIdentifier routerIdentifier;
+
+    /**
+     * Constructor to initialize parameters.
+     *
+     * @param routeDish routing distinguisher instance
+     * @param routeInstance routing protocol instance
+     * @param asNum AS number
+     * @param domainIdentifier BGP-LS domain
+     * @param areaId Area ID
+     * @param routerIdentifier IGP router ID
+     */
+    public IpDeviceIdentifier(RouteDistinguisher routeDish, RouteInstance routeInstance, AsNumber asNum,
+                           DomainId domainIdentifier, AreaId areaId, RouteIdentifier routerIdentifier) {
+        this.routeDish = routeDish;
+        this.areaId = areaId;
+        this.asNum = asNum;
+        this.domainIdentifier = domainIdentifier;
+        this.routeInstance = routeInstance;
+        this.routerIdentifier = routerIdentifier;
+    }
+
+    /**
+     * Obtains Route Distinguisher of Ip Device.
+     *
+     * @return Area ID
+     */
+    public RouteDistinguisher routeDish() {
+        return routeDish;
+    }
+
+    /**
+     * Obtains Area ID if Ip Device.
+     *
+     * @return Area ID
+     */
+    public AreaId areaId() {
+        return areaId;
+    }
+
+    /**
+     * Obtains AS number of Ip Device.
+     *
+     * @return AS number
+     */
+    public AsNumber asNum() {
+        return asNum;
+    }
+
+    /**
+     * Obtains domain identifier of Ip Device.
+     *
+     * @return domain identifier
+     */
+    public DomainId domainIdentifier() {
+        return domainIdentifier;
+    }
+
+    /**
+     * Obtains Router id of Ip Device.
+     *
+     * @return Router id
+     */
+    public RouteIdentifier routerIdentifier() {
+        return routerIdentifier;
+    }
+
+    /**
+     * Obtains routing protocol instance.
+     *
+     * @return routing protocol instance
+     */
+    public RouteInstance routeInstance() {
+        return routeInstance;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(routeDish, areaId, asNum, domainIdentifier, routerIdentifier, routeInstance);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+
+        if (obj instanceof IpDeviceIdentifier) {
+            IpDeviceIdentifier other = (IpDeviceIdentifier) obj;
+            return Objects.equals(areaId, other.areaId) && Objects.equals(asNum, other.asNum)
+                    && Objects.equals(domainIdentifier, other.domainIdentifier)
+                    && Objects.equals(routerIdentifier, other.routerIdentifier)
+                    && Objects.equals(routeInstance, other.routeInstance)
+                    && Objects.equals(routeDish, other.routeDish);
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .omitNullValues()
+                .add("areaId", areaId)
+                .add("asNum", asNum)
+                .add("domainIdentifier", domainIdentifier)
+                .add("routerIdentifier", routerIdentifier)
+                .add("routeInstance", routeInstance)
+                .add("routeDish", routeDish)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpLink.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpLink.java
index d632d2d..22cec15 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpLink.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpLink.java
@@ -1,54 +1,54 @@
-/*
- * 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.iptopology.api;
-
-import org.onosproject.net.Annotated;
-import org.onosproject.net.NetworkResource;
-import org.onosproject.net.Provided;
-
-/**
- * Abstraction of a network ip link.
- */
-public interface IpLink extends Annotated, Provided, NetworkResource {
-
-    /**
-     * Returns source termination point of link.
-     *
-     * @return source termination point of link
-     */
-    TerminationPoint src();
-
-    /**
-     * Returns destination termination point of link.
-     *
-     * @return destination termination point of link
-     */
-    TerminationPoint dst();
-
-    /**
-     * Returns link identifier details.
-     *
-     * @return link identifier details
-     */
-    IpLinkIdentifier linkIdentifier();
-
-    /**
-     * Returns the link traffic engineering parameters.
-     *
-     * @return links traffic engineering parameters
-     */
-    LinkTed linkTed();
+/*
+ * 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.iptopology.api;
+
+import org.onosproject.net.Annotated;
+import org.onosproject.net.NetworkResource;
+import org.onosproject.net.Provided;
+
+/**
+ * Abstraction of a network ip link.
+ */
+public interface IpLink extends Annotated, Provided, NetworkResource {
+
+    /**
+     * Returns source termination point of link.
+     *
+     * @return source termination point of link
+     */
+    TerminationPoint src();
+
+    /**
+     * Returns destination termination point of link.
+     *
+     * @return destination termination point of link
+     */
+    TerminationPoint dst();
+
+    /**
+     * Returns link identifier details.
+     *
+     * @return link identifier details
+     */
+    IpLinkIdentifier linkIdentifier();
+
+    /**
+     * Returns the link traffic engineering parameters.
+     *
+     * @return links traffic engineering parameters
+     */
+    LinkTed linkTed();
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpLinkIdentifier.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpLinkIdentifier.java
index 8522f94..497516b 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpLinkIdentifier.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/IpLinkIdentifier.java
@@ -1,161 +1,161 @@
-/*
- * 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.iptopology.api;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-
-import java.util.Objects;
-
-import org.onlab.packet.Ip4Address;
-import org.onlab.packet.Ip6Address;
-
-/**
- * Represents Ip Link Identifier.
- */
-public class IpLinkIdentifier {
-    private final InterfaceIdentifier localIndentifier;
-    private final InterfaceIdentifier remoteIndentifier;
-    private final Ip4Address localIpv4Addr;
-    private final Ip4Address remoteIpv4Addr;
-    private final Ip6Address localIpv6Addr;
-    private final Ip6Address remoteIpv6Addr;
-    private final TopologyId topologyId;
-
-    /**
-     * Constructor to initialize its parameters.
-     *
-     * @param localIndentifier  local interface identifier of the link
-     * @param remoteIndentifier remote interface identifier of the link
-     * @param localIpv4Addr     local IPv4 address of the link
-     * @param remoteIpv4Addr    remote IPv4 address of the link
-     * @param localIpv6Addr     local IPv6 address of the link
-     * @param remoteIpv6Addr    remote IPv6 address of the link
-     * @param topologyId        link topology identifier
-     */
-    public IpLinkIdentifier(InterfaceIdentifier localIndentifier, InterfaceIdentifier remoteIndentifier,
-                            Ip4Address localIpv4Addr, Ip4Address remoteIpv4Addr, Ip6Address localIpv6Addr,
-                            Ip6Address remoteIpv6Addr, TopologyId topologyId) {
-        this.localIndentifier = localIndentifier;
-        this.remoteIndentifier = remoteIndentifier;
-        this.localIpv4Addr = localIpv4Addr;
-        this.remoteIpv4Addr = remoteIpv4Addr;
-        this.localIpv6Addr = localIpv6Addr;
-        this.remoteIpv6Addr = remoteIpv6Addr;
-        this.topologyId = topologyId;
-    }
-
-    /**
-     * Obtains link local identifier.
-     *
-     * @return link local identifier
-     */
-    public InterfaceIdentifier localIndentifier() {
-        return localIndentifier;
-    }
-
-    /**
-     * Obtains link local identifier.
-     *
-     * @return link local identifier
-     */
-    public InterfaceIdentifier remoteIndentifier() {
-        return remoteIndentifier;
-    }
-
-    /**
-     * Obtains local IPv4 address of the link.
-     *
-     * @return local IPv4  address of the link
-     */
-    public Ip4Address localIpv4Addr() {
-        return localIpv4Addr;
-    }
-
-    /**
-     * Obtains remote IPv4 address of the link.
-     *
-     * @return remote IPv4  address of the link
-     */
-    public Ip4Address remoteIpv4Addr() {
-        return remoteIpv4Addr;
-    }
-
-    /**
-     * Obtains local IPv6 address of the link.
-     *
-     * @return local IPv6 address of the link
-     */
-    public Ip6Address localIpv6Addr() {
-        return localIpv6Addr;
-    }
-
-    /**
-     * Obtains remote IPv6 address of the link.
-     *
-     * @return remote IPv6 address of the link
-     */
-    public Ip6Address remoteIpv6Addr() {
-        return remoteIpv6Addr;
-    }
-
-    /**
-     * Obtains Topology ID of the link.
-     *
-     * @return Topology ID of the link
-     */
-    public TopologyId topologyId() {
-        return topologyId;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(localIndentifier, remoteIndentifier, localIpv4Addr, remoteIpv4Addr,
-                localIpv6Addr, remoteIpv6Addr, topologyId);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-
-        if (obj instanceof IpLinkIdentifier) {
-            IpLinkIdentifier other = (IpLinkIdentifier) obj;
-            return Objects.equals(topologyId, other.topologyId)
-                    && Objects.equals(localIndentifier, other.localIndentifier)
-                    && Objects.equals(remoteIndentifier, other.remoteIndentifier)
-                    && Objects.equals(localIpv4Addr, other.localIpv4Addr)
-                    && Objects.equals(remoteIpv4Addr, other.remoteIpv4Addr)
-                    && Objects.equals(localIpv6Addr, other.localIpv6Addr)
-                    && Objects.equals(remoteIpv6Addr, other.remoteIpv6Addr);
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .omitNullValues()
-                .add("localIndentifier", localIndentifier)
-                .add("remoteIndentifier", remoteIndentifier)
-                .add("localIpv4Addr", localIpv4Addr)
-                .add("remoteIpv4Addr", remoteIpv4Addr)
-                .add("localIpv6Addr", localIpv6Addr)
-                .add("remoteIpv6Addr", remoteIpv6Addr)
-                .add("topologyId", topologyId)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+
+import java.util.Objects;
+
+import org.onlab.packet.Ip4Address;
+import org.onlab.packet.Ip6Address;
+
+/**
+ * Represents Ip Link Identifier.
+ */
+public class IpLinkIdentifier {
+    private final InterfaceIdentifier localIndentifier;
+    private final InterfaceIdentifier remoteIndentifier;
+    private final Ip4Address localIpv4Addr;
+    private final Ip4Address remoteIpv4Addr;
+    private final Ip6Address localIpv6Addr;
+    private final Ip6Address remoteIpv6Addr;
+    private final TopologyId topologyId;
+
+    /**
+     * Constructor to initialize its parameters.
+     *
+     * @param localIndentifier  local interface identifier of the link
+     * @param remoteIndentifier remote interface identifier of the link
+     * @param localIpv4Addr     local IPv4 address of the link
+     * @param remoteIpv4Addr    remote IPv4 address of the link
+     * @param localIpv6Addr     local IPv6 address of the link
+     * @param remoteIpv6Addr    remote IPv6 address of the link
+     * @param topologyId        link topology identifier
+     */
+    public IpLinkIdentifier(InterfaceIdentifier localIndentifier, InterfaceIdentifier remoteIndentifier,
+                            Ip4Address localIpv4Addr, Ip4Address remoteIpv4Addr, Ip6Address localIpv6Addr,
+                            Ip6Address remoteIpv6Addr, TopologyId topologyId) {
+        this.localIndentifier = localIndentifier;
+        this.remoteIndentifier = remoteIndentifier;
+        this.localIpv4Addr = localIpv4Addr;
+        this.remoteIpv4Addr = remoteIpv4Addr;
+        this.localIpv6Addr = localIpv6Addr;
+        this.remoteIpv6Addr = remoteIpv6Addr;
+        this.topologyId = topologyId;
+    }
+
+    /**
+     * Obtains link local identifier.
+     *
+     * @return link local identifier
+     */
+    public InterfaceIdentifier localIndentifier() {
+        return localIndentifier;
+    }
+
+    /**
+     * Obtains link local identifier.
+     *
+     * @return link local identifier
+     */
+    public InterfaceIdentifier remoteIndentifier() {
+        return remoteIndentifier;
+    }
+
+    /**
+     * Obtains local IPv4 address of the link.
+     *
+     * @return local IPv4  address of the link
+     */
+    public Ip4Address localIpv4Addr() {
+        return localIpv4Addr;
+    }
+
+    /**
+     * Obtains remote IPv4 address of the link.
+     *
+     * @return remote IPv4  address of the link
+     */
+    public Ip4Address remoteIpv4Addr() {
+        return remoteIpv4Addr;
+    }
+
+    /**
+     * Obtains local IPv6 address of the link.
+     *
+     * @return local IPv6 address of the link
+     */
+    public Ip6Address localIpv6Addr() {
+        return localIpv6Addr;
+    }
+
+    /**
+     * Obtains remote IPv6 address of the link.
+     *
+     * @return remote IPv6 address of the link
+     */
+    public Ip6Address remoteIpv6Addr() {
+        return remoteIpv6Addr;
+    }
+
+    /**
+     * Obtains Topology ID of the link.
+     *
+     * @return Topology ID of the link
+     */
+    public TopologyId topologyId() {
+        return topologyId;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(localIndentifier, remoteIndentifier, localIpv4Addr, remoteIpv4Addr,
+                localIpv6Addr, remoteIpv6Addr, topologyId);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+
+        if (obj instanceof IpLinkIdentifier) {
+            IpLinkIdentifier other = (IpLinkIdentifier) obj;
+            return Objects.equals(topologyId, other.topologyId)
+                    && Objects.equals(localIndentifier, other.localIndentifier)
+                    && Objects.equals(remoteIndentifier, other.remoteIndentifier)
+                    && Objects.equals(localIpv4Addr, other.localIpv4Addr)
+                    && Objects.equals(remoteIpv4Addr, other.remoteIpv4Addr)
+                    && Objects.equals(localIpv6Addr, other.localIpv6Addr)
+                    && Objects.equals(remoteIpv6Addr, other.remoteIpv6Addr);
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .omitNullValues()
+                .add("localIndentifier", localIndentifier)
+                .add("remoteIndentifier", remoteIndentifier)
+                .add("localIpv4Addr", localIpv4Addr)
+                .add("remoteIpv4Addr", remoteIpv4Addr)
+                .add("localIpv6Addr", localIpv6Addr)
+                .add("remoteIpv6Addr", remoteIpv6Addr)
+                .add("topologyId", topologyId)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/PrefixIdentifier.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/PrefixIdentifier.java
index b41b5d7..76f622a 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/PrefixIdentifier.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/PrefixIdentifier.java
@@ -1,98 +1,98 @@
-/*
- * 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.iptopology.api;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-
-import java.util.Objects;
-
-/**
- * This class provides Prefix Identifier details.
- */
-public class PrefixIdentifier {
-    private final TopologyId topologyId;
-    private final RouteType routeType;
-    private final IpReachability ipReach;
-
-    /**
-     * Constructor to initialize its parameters.
-     *
-     * @param topologyId topology ID of prefix
-     * @param routeType OSPF Route type of the prefix
-     * @param ipReach IP address prefix reachability information
-     */
-    public PrefixIdentifier(TopologyId topologyId, RouteType routeType, IpReachability ipReach) {
-        this.topologyId = topologyId;
-        this.routeType = routeType;
-        this.ipReach = ipReach;
-    }
-
-    /**
-     * Provides topology ID of prefix.
-     *
-     * @return topology id
-     */
-    public TopologyId topologyId() {
-        return this.topologyId;
-    }
-
-    /**
-     * Provides IP address prefix reachability information.
-     *
-     * @return IP address prefix
-     */
-    public IpReachability ipReach() {
-        return this.ipReach;
-    }
-
-    /**
-     * Provides OSPF Route type of the prefix.
-     *
-     * @return Route type
-     */
-    public RouteType routeType() {
-        return this.routeType;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(topologyId, routeType, ipReach);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-
-        if (obj instanceof PrefixIdentifier) {
-            PrefixIdentifier other = (PrefixIdentifier) obj;
-            return Objects.equals(topologyId, other.topologyId) && Objects.equals(routeType, other.routeType)
-                   && Objects.equals(ipReach, other.ipReach);
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .omitNullValues()
-                .add("routeType", routeType)
-                .add("ipReach", ipReach)
-                .add("topologyId", topologyId)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+
+import java.util.Objects;
+
+/**
+ * This class provides Prefix Identifier details.
+ */
+public class PrefixIdentifier {
+    private final TopologyId topologyId;
+    private final RouteType routeType;
+    private final IpReachability ipReach;
+
+    /**
+     * Constructor to initialize its parameters.
+     *
+     * @param topologyId topology ID of prefix
+     * @param routeType OSPF Route type of the prefix
+     * @param ipReach IP address prefix reachability information
+     */
+    public PrefixIdentifier(TopologyId topologyId, RouteType routeType, IpReachability ipReach) {
+        this.topologyId = topologyId;
+        this.routeType = routeType;
+        this.ipReach = ipReach;
+    }
+
+    /**
+     * Provides topology ID of prefix.
+     *
+     * @return topology id
+     */
+    public TopologyId topologyId() {
+        return this.topologyId;
+    }
+
+    /**
+     * Provides IP address prefix reachability information.
+     *
+     * @return IP address prefix
+     */
+    public IpReachability ipReach() {
+        return this.ipReach;
+    }
+
+    /**
+     * Provides OSPF Route type of the prefix.
+     *
+     * @return Route type
+     */
+    public RouteType routeType() {
+        return this.routeType;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(topologyId, routeType, ipReach);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+
+        if (obj instanceof PrefixIdentifier) {
+            PrefixIdentifier other = (PrefixIdentifier) obj;
+            return Objects.equals(topologyId, other.topologyId) && Objects.equals(routeType, other.routeType)
+                   && Objects.equals(ipReach, other.ipReach);
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .omitNullValues()
+                .add("routeType", routeType)
+                .add("ipReach", ipReach)
+                .add("topologyId", topologyId)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/TerminationPoint.java b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/TerminationPoint.java
index 9c21cb4..52d5dd8 100644
--- a/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/TerminationPoint.java
+++ b/apps/iptopology-api/src/main/java/org/onosproject/iptopology/api/TerminationPoint.java
@@ -1,104 +1,104 @@
-/*
- * 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.iptopology.api;
-
-import java.util.Objects;
-
-import org.onosproject.net.DeviceId;
-import org.onosproject.net.ElementId;
-
-import com.google.common.base.MoreObjects;
-
-/**
- * Abstraction of a network termination point expressed as a pair of the network element identifier and device
- * interface.
- */
-public class TerminationPoint {
-    private final ElementId elementId;
-    private final DeviceInterface deviceInterface;
-
-    /**
-     * Constructor to initialize its parameters.
-     *
-     * @param elementId network element identifier
-     * @param deviceInterface device interface
-     */
-    public TerminationPoint(ElementId elementId, DeviceInterface deviceInterface) {
-        this.elementId = elementId;
-        this.deviceInterface = deviceInterface;
-    }
-
-    /**
-     * Returns the network element identifier.
-     *
-     * @return element identifier
-     */
-    public ElementId elementId() {
-        return elementId;
-    }
-
-    /**
-     * Returns the identifier of the infrastructure device if the termination
-     * point belongs to a network element which is indeed an ip
-     * device.
-     *
-     * @return network element identifier as a device identifier
-     * @throws java.lang.IllegalStateException if termination point is not
-     *                                         associated with a device
-     */
-    public DeviceId deviceId() {
-        if (elementId instanceof DeviceId) {
-            return (DeviceId) elementId;
-        }
-        throw new IllegalStateException("Termination point not associated " +
-                "with an ip device");
-    }
-
-    /**
-     * Returns Device interface details.
-     *
-     * @return device interface details
-     */
-    public DeviceInterface deviceInterface() {
-        return deviceInterface;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(elementId, deviceInterface);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-        if (obj instanceof TerminationPoint) {
-            final TerminationPoint other = (TerminationPoint) obj;
-            return Objects.equals(this.elementId, other.elementId)
-                    && Objects.equals(this.deviceInterface, other.deviceInterface);
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(this)
-                .add("elementId", elementId)
-                .add("deviceInterface", deviceInterface)
-                .toString();
-    }
+/*
+ * 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.iptopology.api;
+
+import java.util.Objects;
+
+import org.onosproject.net.DeviceId;
+import org.onosproject.net.ElementId;
+
+import com.google.common.base.MoreObjects;
+
+/**
+ * Abstraction of a network termination point expressed as a pair of the network element identifier and device
+ * interface.
+ */
+public class TerminationPoint {
+    private final ElementId elementId;
+    private final DeviceInterface deviceInterface;
+
+    /**
+     * Constructor to initialize its parameters.
+     *
+     * @param elementId network element identifier
+     * @param deviceInterface device interface
+     */
+    public TerminationPoint(ElementId elementId, DeviceInterface deviceInterface) {
+        this.elementId = elementId;
+        this.deviceInterface = deviceInterface;
+    }
+
+    /**
+     * Returns the network element identifier.
+     *
+     * @return element identifier
+     */
+    public ElementId elementId() {
+        return elementId;
+    }
+
+    /**
+     * Returns the identifier of the infrastructure device if the termination
+     * point belongs to a network element which is indeed an ip
+     * device.
+     *
+     * @return network element identifier as a device identifier
+     * @throws java.lang.IllegalStateException if termination point is not
+     *                                         associated with a device
+     */
+    public DeviceId deviceId() {
+        if (elementId instanceof DeviceId) {
+            return (DeviceId) elementId;
+        }
+        throw new IllegalStateException("Termination point not associated " +
+                "with an ip device");
+    }
+
+    /**
+     * Returns Device interface details.
+     *
+     * @return device interface details
+     */
+    public DeviceInterface deviceInterface() {
+        return deviceInterface;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(elementId, deviceInterface);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+        if (obj instanceof TerminationPoint) {
+            final TerminationPoint other = (TerminationPoint) obj;
+            return Objects.equals(this.elementId, other.elementId)
+                    && Objects.equals(this.deviceInterface, other.deviceInterface);
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return MoreObjects.toStringHelper(this)
+                .add("elementId", elementId)
+                .add("deviceInterface", deviceInterface)
+                .toString();
+    }
 }
\ No newline at end of file
diff --git a/apps/mfwd/src/main/java/org/onosproject/mfwd/cli/McastJoinCommand.java b/apps/mfwd/src/main/java/org/onosproject/mfwd/cli/McastJoinCommand.java
index 3f22e7a..707dbf0 100644
--- a/apps/mfwd/src/main/java/org/onosproject/mfwd/cli/McastJoinCommand.java
+++ b/apps/mfwd/src/main/java/org/onosproject/mfwd/cli/McastJoinCommand.java
@@ -1,75 +1,75 @@
-/*
- * Copyright 2014-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.mfwd.cli;
-
-import org.apache.felix.scr.annotations.Reference;
-import org.apache.felix.scr.annotations.ReferenceCardinality;
-import org.apache.karaf.shell.commands.Argument;
-import org.apache.karaf.shell.commands.Command;
-import org.onosproject.cli.AbstractShellCommand;
-import org.onosproject.mfwd.impl.McastForwarding;
-import org.onosproject.net.ConnectPoint;
-import org.onosproject.net.mcast.McastRoute;
-import org.onosproject.net.mcast.MulticastRouteService;
-
-/**
- * Installs a source, multicast group flow.
- */
-@Command(scope = "onos", name = "mcast-join",
-         description = "Installs a source, multicast group flow")
-public class McastJoinCommand extends AbstractShellCommand {
-
-    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
-    MulticastRouteService mcastRouteManager = AbstractShellCommand.get(MulticastRouteService.class);
-
-    @Argument(index = 0, name = "sAddr",
-              description = "IP Address of the multicast source. '*' can be used for any source (*, G) entry",
-              required = true, multiValued = false)
-    String sAddr = null;
-
-    @Argument(index = 1, name = "gAddr",
-              description = "IP Address of the multicast group",
-              required = true, multiValued = false)
-    String gAddr = null;
-
-    @Argument(index = 2, name = "ingressPort",
-            description = "Ingress port of:XXXXXXXXXX/XX",
-            required = false, multiValued = false)
-    String ingressPort = null;
-
-    @Argument(index = 3, name = "ports",
-              description = "Egress ports of:XXXXXXXXXX/XX...",
-              required = false, multiValued = true)
-    String[] ports = null;
-
-    @Override
-    protected void execute() {
-
-        McastRoute mRoute = McastForwarding.createStaticRoute(sAddr, gAddr);
-        mcastRouteManager.add(mRoute);
-
-        ConnectPoint ingress = ConnectPoint.deviceConnectPoint(ingressPort);
-        mcastRouteManager.addSource(mRoute, ingress);
-
-        for (String egCP : ports) {
-            log.debug("Egress port provided: " + egCP);
-            ConnectPoint egress = ConnectPoint.deviceConnectPoint(egCP);
-            mcastRouteManager.addSink(mRoute, egress);
-
-        }
-        print("Added the mcast route");
-    }
-}
+/*
+ * Copyright 2014-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.mfwd.cli;
+
+import org.apache.felix.scr.annotations.Reference;
+import org.apache.felix.scr.annotations.ReferenceCardinality;
+import org.apache.karaf.shell.commands.Argument;
+import org.apache.karaf.shell.commands.Command;
+import org.onosproject.cli.AbstractShellCommand;
+import org.onosproject.mfwd.impl.McastForwarding;
+import org.onosproject.net.ConnectPoint;
+import org.onosproject.net.mcast.McastRoute;
+import org.onosproject.net.mcast.MulticastRouteService;
+
+/**
+ * Installs a source, multicast group flow.
+ */
+@Command(scope = "onos", name = "mcast-join",
+         description = "Installs a source, multicast group flow")
+public class McastJoinCommand extends AbstractShellCommand {
+
+    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
+    MulticastRouteService mcastRouteManager = AbstractShellCommand.get(MulticastRouteService.class);
+
+    @Argument(index = 0, name = "sAddr",
+              description = "IP Address of the multicast source. '*' can be used for any source (*, G) entry",
+              required = true, multiValued = false)
+    String sAddr = null;
+
+    @Argument(index = 1, name = "gAddr",
+              description = "IP Address of the multicast group",
+              required = true, multiValued = false)
+    String gAddr = null;
+
+    @Argument(index = 2, name = "ingressPort",
+            description = "Ingress port of:XXXXXXXXXX/XX",
+            required = false, multiValued = false)
+    String ingressPort = null;
+
+    @Argument(index = 3, name = "ports",
+              description = "Egress ports of:XXXXXXXXXX/XX...",
+              required = false, multiValued = true)
+    String[] ports = null;
+
+    @Override
+    protected void execute() {
+
+        McastRoute mRoute = McastForwarding.createStaticRoute(sAddr, gAddr);
+        mcastRouteManager.add(mRoute);
+
+        ConnectPoint ingress = ConnectPoint.deviceConnectPoint(ingressPort);
+        mcastRouteManager.addSource(mRoute, ingress);
+
+        for (String egCP : ports) {
+            log.debug("Egress port provided: " + egCP);
+            ConnectPoint egress = ConnectPoint.deviceConnectPoint(egCP);
+            mcastRouteManager.addSink(mRoute, egress);
+
+        }
+        print("Added the mcast route");
+    }
+}
diff --git a/apps/mfwd/src/main/java/org/onosproject/mfwd/cli/package-info.java b/apps/mfwd/src/main/java/org/onosproject/mfwd/cli/package-info.java
index 7b5ed39..bff76fc 100644
--- a/apps/mfwd/src/main/java/org/onosproject/mfwd/cli/package-info.java
+++ b/apps/mfwd/src/main/java/org/onosproject/mfwd/cli/package-info.java
@@ -1,5 +1,5 @@
-/**
- * Sample Multicast forwarding framework using intents.
- */
-package org.onosproject.mfwd.cli;
-
+/**
+ * Sample Multicast forwarding framework using intents.
+ */
+package org.onosproject.mfwd.cli;
+
diff --git a/apps/vtn/vtnrsc/src/main/java/org/onosproject/vtnrsc/Router.java b/apps/vtn/vtnrsc/src/main/java/org/onosproject/vtnrsc/Router.java
index e853ec2..3c6d881 100644
--- a/apps/vtn/vtnrsc/src/main/java/org/onosproject/vtnrsc/Router.java
+++ b/apps/vtn/vtnrsc/src/main/java/org/onosproject/vtnrsc/Router.java
@@ -1,102 +1,102 @@
-/*
- * 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.vtnrsc;
-
-import java.util.List;
-
-/**
- * Representation of a Router.
- */
-public interface Router {
-
-    /**
-     * Coarse classification of the type of the Router.
-     */
-    public enum Status {
-        /**
-         * Signifies that a router is currently active.
-         */
-        ACTIVE,
-        /**
-         * Signifies that a router is currently inactive.
-         */
-        INACTIVE
-    }
-
-    /**
-     * Returns the router identifier.
-     *
-     * @return identifier
-     */
-    RouterId id();
-
-    /**
-     * Returns the router Name.
-     *
-     * @return routerName
-     */
-    String name();
-
-    /**
-     * Returns the router admin state.
-     *
-     * @return true or false
-     */
-    boolean adminStateUp();
-
-    /**
-     * Returns the status of router.
-     *
-     * @return RouterStatus
-     */
-    Status status();
-
-    /**
-     * Returns the distributed status of this router.
-     * If true, indicates a distributed router.
-     *
-     * @return true or false
-     */
-    boolean distributed();
-
-    /**
-     * Returns the RouterGateway of router.
-     *
-     * @return routerGateway
-     */
-    RouterGateway externalGatewayInfo();
-
-    /**
-     * Returns the gatewayPortid of router.
-     *
-     * @return virtualPortId
-     */
-    VirtualPortId gatewayPortid();
-
-    /**
-     * Returns the owner(tenant) of this router.
-     *
-     * @return tenantId
-     */
-    TenantId tenantId();
-
-    /**
-     * Returns the router list of router.
-     *
-     * @return routes
-     */
-    List<String> routes();
-}
+/*
+ * 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.vtnrsc;
+
+import java.util.List;
+
+/**
+ * Representation of a Router.
+ */
+public interface Router {
+
+    /**
+     * Coarse classification of the type of the Router.
+     */
+    public enum Status {
+        /**
+         * Signifies that a router is currently active.
+         */
+        ACTIVE,
+        /**
+         * Signifies that a router is currently inactive.
+         */
+        INACTIVE
+    }
+
+    /**
+     * Returns the router identifier.
+     *
+     * @return identifier
+     */
+    RouterId id();
+
+    /**
+     * Returns the router Name.
+     *
+     * @return routerName
+     */
+    String name();
+
+    /**
+     * Returns the router admin state.
+     *
+     * @return true or false
+     */
+    boolean adminStateUp();
+
+    /**
+     * Returns the status of router.
+     *
+     * @return RouterStatus
+     */
+    Status status();
+
+    /**
+     * Returns the distributed status of this router.
+     * If true, indicates a distributed router.
+     *
+     * @return true or false
+     */
+    boolean distributed();
+
+    /**
+     * Returns the RouterGateway of router.
+     *
+     * @return routerGateway
+     */
+    RouterGateway externalGatewayInfo();
+
+    /**
+     * Returns the gatewayPortid of router.
+     *
+     * @return virtualPortId
+     */
+    VirtualPortId gatewayPortid();
+
+    /**
+     * Returns the owner(tenant) of this router.
+     *
+     * @return tenantId
+     */
+    TenantId tenantId();
+
+    /**
+     * Returns the router list of router.
+     *
+     * @return routes
+     */
+    List<String> routes();
+}
diff --git a/apps/vtn/vtnrsc/src/main/java/org/onosproject/vtnrsc/RouterGateway.java b/apps/vtn/vtnrsc/src/main/java/org/onosproject/vtnrsc/RouterGateway.java
index 9a75556..da14fae 100644
--- a/apps/vtn/vtnrsc/src/main/java/org/onosproject/vtnrsc/RouterGateway.java
+++ b/apps/vtn/vtnrsc/src/main/java/org/onosproject/vtnrsc/RouterGateway.java
@@ -1,108 +1,108 @@
-/*
- * 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.vtnrsc;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-import static com.google.common.base.Preconditions.checkNotNull;
-
-import java.util.Collection;
-import java.util.Objects;
-
-/**
- * Representation of a Router gateway.
- */
-public final class RouterGateway {
-
-    private final TenantNetworkId networkId;
-    private final boolean enableSnat;
-    private final Collection<FixedIp> externalFixedIps;
-
-    // Public construction is prohibited
-    private RouterGateway(TenantNetworkId networkId, boolean enableSnat,
-                         Collection<FixedIp> externalFixedIps) {
-        this.networkId = checkNotNull(networkId, "networkId cannot be null");
-        this.enableSnat = checkNotNull(enableSnat, "enableSnat cannot be null");
-        this.externalFixedIps = checkNotNull(externalFixedIps, "externalFixedIps cannot be null");
-    }
-
-    /**
-     * Creates router gateway object.
-     *
-     * @param networkId network identifier
-     * @param enableSnat SNAT enable or not
-     * @param externalFixedIps external fixed IP
-     * @return RouterGateway
-     */
-    public static RouterGateway routerGateway(TenantNetworkId networkId, boolean enableSnat,
-                                              Collection<FixedIp> externalFixedIps) {
-        return new RouterGateway(networkId, enableSnat, externalFixedIps);
-    }
-
-    /**
-     * Returns network identifier.
-     *
-     * @return networkId
-     */
-    public TenantNetworkId networkId() {
-        return networkId;
-    }
-
-    /**
-     * Return SNAT enable or not.
-     *
-     * @return enableSnat
-     */
-    public boolean enableSnat() {
-        return enableSnat;
-    }
-
-    /**
-     * Return external fixed Ip.
-     *
-     * @return externalFixedIps
-     */
-    public Collection<FixedIp> externalFixedIps() {
-        return externalFixedIps;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(networkId, enableSnat, externalFixedIps);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-        if (obj instanceof RouterGateway) {
-            final RouterGateway that = (RouterGateway) obj;
-            return Objects.equals(this.networkId, that.networkId)
-                    && Objects.equals(this.enableSnat, that.enableSnat)
-                    && Objects.equals(this.externalFixedIps, that.externalFixedIps);
-        }
-        return false;
-    }
-
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .add("networkId", networkId)
-                .add("enableSnat", enableSnat)
-                .add("externalFixedIps", externalFixedIps)
-                .toString();
-    }
-}
+/*
+ * 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.vtnrsc;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+import static com.google.common.base.Preconditions.checkNotNull;
+
+import java.util.Collection;
+import java.util.Objects;
+
+/**
+ * Representation of a Router gateway.
+ */
+public final class RouterGateway {
+
+    private final TenantNetworkId networkId;
+    private final boolean enableSnat;
+    private final Collection<FixedIp> externalFixedIps;
+
+    // Public construction is prohibited
+    private RouterGateway(TenantNetworkId networkId, boolean enableSnat,
+                         Collection<FixedIp> externalFixedIps) {
+        this.networkId = checkNotNull(networkId, "networkId cannot be null");
+        this.enableSnat = checkNotNull(enableSnat, "enableSnat cannot be null");
+        this.externalFixedIps = checkNotNull(externalFixedIps, "externalFixedIps cannot be null");
+    }
+
+    /**
+     * Creates router gateway object.
+     *
+     * @param networkId network identifier
+     * @param enableSnat SNAT enable or not
+     * @param externalFixedIps external fixed IP
+     * @return RouterGateway
+     */
+    public static RouterGateway routerGateway(TenantNetworkId networkId, boolean enableSnat,
+                                              Collection<FixedIp> externalFixedIps) {
+        return new RouterGateway(networkId, enableSnat, externalFixedIps);
+    }
+
+    /**
+     * Returns network identifier.
+     *
+     * @return networkId
+     */
+    public TenantNetworkId networkId() {
+        return networkId;
+    }
+
+    /**
+     * Return SNAT enable or not.
+     *
+     * @return enableSnat
+     */
+    public boolean enableSnat() {
+        return enableSnat;
+    }
+
+    /**
+     * Return external fixed Ip.
+     *
+     * @return externalFixedIps
+     */
+    public Collection<FixedIp> externalFixedIps() {
+        return externalFixedIps;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(networkId, enableSnat, externalFixedIps);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+        if (obj instanceof RouterGateway) {
+            final RouterGateway that = (RouterGateway) obj;
+            return Objects.equals(this.networkId, that.networkId)
+                    && Objects.equals(this.enableSnat, that.enableSnat)
+                    && Objects.equals(this.externalFixedIps, that.externalFixedIps);
+        }
+        return false;
+    }
+
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .add("networkId", networkId)
+                .add("enableSnat", enableSnat)
+                .add("externalFixedIps", externalFixedIps)
+                .toString();
+    }
+}
diff --git a/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnEventuallyConsistentMapTest.java b/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnEventuallyConsistentMapTest.java
index 68b7d68..60b64cc 100644
--- a/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnEventuallyConsistentMapTest.java
+++ b/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnEventuallyConsistentMapTest.java
@@ -1,242 +1,242 @@
-/*
- * 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.vtnrsc.util;
-
-import java.util.Collection;
-import java.util.HashMap;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.ScheduledExecutorService;
-import java.util.concurrent.TimeUnit;
-import java.util.function.BiFunction;
-
-import org.onlab.util.KryoNamespace;
-import org.onosproject.cluster.NodeId;
-import org.onosproject.store.Timestamp;
-
-import static org.onosproject.store.service.EventuallyConsistentMapEvent.Type.*;
-import org.onosproject.store.service.EventuallyConsistentMapListener;
-import org.onosproject.store.service.EventuallyConsistentMapEvent;
-import org.onosproject.store.service.EventuallyConsistentMapBuilder;
-import org.onosproject.store.service.EventuallyConsistentMap;
-
-/**
- * Testing version of an Eventually Consistent Map.
- */
-
-public final class VtnEventuallyConsistentMapTest<K, V> extends VtnEventuallyConsistentMapAdapter<K, V> {
-
-    private final HashMap<K, V> map;
-    private final String mapName;
-    private final List<EventuallyConsistentMapListener<K, V>> listeners;
-    private final BiFunction<K, V, Collection<NodeId>> peerUpdateFunction;
-
-    private VtnEventuallyConsistentMapTest(String mapName,
-            BiFunction<K, V, Collection<NodeId>> peerUpdateFunction) {
-        map = new HashMap<>();
-        listeners = new LinkedList<>();
-        this.mapName = mapName;
-        this.peerUpdateFunction = peerUpdateFunction;
-    }
-
-    /**
-     * Notify all listeners of an event.
-     */
-    private void notifyListeners(EventuallyConsistentMapEvent<K, V> event) {
-        listeners.forEach(
-                listener -> listener.event(event)
-                );
-    }
-
-    @Override
-    public int size() {
-        return map.size();
-    }
-
-    @Override
-    public boolean isEmpty() {
-        return map.isEmpty();
-    }
-
-    @Override
-    public boolean containsKey(K key) {
-        return map.containsKey(key);
-    }
-
-    @Override
-    public boolean containsValue(V value) {
-        return map.containsValue(value);
-    }
-
-    @Override
-    public V get(K key) {
-        return map.get(key);
-    }
-
-    @Override
-    public void put(K key, V value) {
-        map.put(key, value);
-        EventuallyConsistentMapEvent<K, V> addEvent =
-                new EventuallyConsistentMapEvent<>(mapName, PUT, key, value);
-        notifyListeners(addEvent);
-        if (peerUpdateFunction != null) {
-            peerUpdateFunction.apply(key, value);
-        }
-    }
-
-    @Override
-    public V remove(K key) {
-        V result = map.remove(key);
-        if (result != null) {
-            EventuallyConsistentMapEvent<K, V> removeEvent =
-                    new EventuallyConsistentMapEvent<>(mapName, REMOVE,
-                            key, map.get(key));
-            notifyListeners(removeEvent);
-        }
-        return result;
-    }
-
-    @Override
-    public void remove(K key, V value) {
-        boolean removed = map.remove(key, value);
-        if (removed) {
-            EventuallyConsistentMapEvent<K, V> removeEvent =
-                    new EventuallyConsistentMapEvent<>(mapName, REMOVE, key, value);
-            notifyListeners(removeEvent);
-        }
-    }
-
-    @Override
-    public V compute(K key, BiFunction<K, V, V> recomputeFunction) {
-        return map.compute(key, recomputeFunction);
-    }
-
-    @Override
-    public void putAll(Map<? extends K, ? extends V> m) {
-        map.putAll(m);
-    }
-
-    @Override
-    public void clear() {
-        map.clear();
-    }
-
-    @Override
-    public Set<K> keySet() {
-        return map.keySet();
-    }
-
-    @Override
-    public Collection<V> values() {
-        return map.values();
-    }
-
-    @Override
-    public Set<Map.Entry<K, V>> entrySet() {
-        return map.entrySet();
-    }
-
-    public static <K, V> Builder<K, V> builder() {
-        return new Builder<>();
-    }
-
-    @Override
-    public void addListener(EventuallyConsistentMapListener<K, V> listener) {
-        listeners.add(listener);
-    }
-
-    @Override
-    public void removeListener(EventuallyConsistentMapListener<K, V> listener) {
-        listeners.remove(listener);
-    }
-
-    public static class Builder<K, V> implements EventuallyConsistentMapBuilder<K, V> {
-        private String name;
-        private BiFunction<K, V, Collection<NodeId>> peerUpdateFunction;
-
-        @Override
-        public EventuallyConsistentMapBuilder<K, V> withName(String name) {
-            this.name = name;
-            return this;
-        }
-
-        @Override
-        public EventuallyConsistentMapBuilder<K, V> withSerializer(KryoNamespace.Builder serializerBuilder) {
-            return this;
-        }
-
-        @Override
-        public EventuallyConsistentMapBuilder<K, V>
-        withTimestampProvider(BiFunction<K, V, Timestamp> timestampProvider) {
-            return this;
-        }
-
-        @Override
-        public EventuallyConsistentMapBuilder<K, V> withEventExecutor(ExecutorService executor) {
-            return this;
-        }
-
-        @Override
-        public EventuallyConsistentMapBuilder<K, V> withCommunicationExecutor(ExecutorService executor) {
-            return this;
-        }
-
-        @Override
-        public EventuallyConsistentMapBuilder<K, V> withBackgroundExecutor(ScheduledExecutorService executor) {
-            return this;
-        }
-
-        @Override
-        public EventuallyConsistentMapBuilder<K, V>
-        withPeerUpdateFunction(BiFunction<K, V, Collection<NodeId>> peerUpdateFunction) {
-            this.peerUpdateFunction = peerUpdateFunction;
-            return this;
-        }
-
-        @Override
-        public EventuallyConsistentMapBuilder<K, V> withTombstonesDisabled() {
-            return this;
-        }
-
-        @Override
-        public EventuallyConsistentMapBuilder<K, V> withAntiEntropyPeriod(long period, TimeUnit unit) {
-            return this;
-        }
-
-        @Override
-        public EventuallyConsistentMapBuilder<K, V> withFasterConvergence() {
-            return this;
-        }
-
-        @Override
-        public EventuallyConsistentMapBuilder<K, V> withPersistence() {
-            return this;
-        }
-
-        @Override
-        public EventuallyConsistentMap<K, V> build() {
-            if (name == null) {
-                name = "test";
-            }
-            return new VtnEventuallyConsistentMapTest<>(name, peerUpdateFunction);
-        }
-    }
-
-}
-
+/*
+ * 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.vtnrsc.util;
+
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.ScheduledExecutorService;
+import java.util.concurrent.TimeUnit;
+import java.util.function.BiFunction;
+
+import org.onlab.util.KryoNamespace;
+import org.onosproject.cluster.NodeId;
+import org.onosproject.store.Timestamp;
+
+import static org.onosproject.store.service.EventuallyConsistentMapEvent.Type.*;
+import org.onosproject.store.service.EventuallyConsistentMapListener;
+import org.onosproject.store.service.EventuallyConsistentMapEvent;
+import org.onosproject.store.service.EventuallyConsistentMapBuilder;
+import org.onosproject.store.service.EventuallyConsistentMap;
+
+/**
+ * Testing version of an Eventually Consistent Map.
+ */
+
+public final class VtnEventuallyConsistentMapTest<K, V> extends VtnEventuallyConsistentMapAdapter<K, V> {
+
+    private final HashMap<K, V> map;
+    private final String mapName;
+    private final List<EventuallyConsistentMapListener<K, V>> listeners;
+    private final BiFunction<K, V, Collection<NodeId>> peerUpdateFunction;
+
+    private VtnEventuallyConsistentMapTest(String mapName,
+            BiFunction<K, V, Collection<NodeId>> peerUpdateFunction) {
+        map = new HashMap<>();
+        listeners = new LinkedList<>();
+        this.mapName = mapName;
+        this.peerUpdateFunction = peerUpdateFunction;
+    }
+
+    /**
+     * Notify all listeners of an event.
+     */
+    private void notifyListeners(EventuallyConsistentMapEvent<K, V> event) {
+        listeners.forEach(
+                listener -> listener.event(event)
+                );
+    }
+
+    @Override
+    public int size() {
+        return map.size();
+    }
+
+    @Override
+    public boolean isEmpty() {
+        return map.isEmpty();
+    }
+
+    @Override
+    public boolean containsKey(K key) {
+        return map.containsKey(key);
+    }
+
+    @Override
+    public boolean containsValue(V value) {
+        return map.containsValue(value);
+    }
+
+    @Override
+    public V get(K key) {
+        return map.get(key);
+    }
+
+    @Override
+    public void put(K key, V value) {
+        map.put(key, value);
+        EventuallyConsistentMapEvent<K, V> addEvent =
+                new EventuallyConsistentMapEvent<>(mapName, PUT, key, value);
+        notifyListeners(addEvent);
+        if (peerUpdateFunction != null) {
+            peerUpdateFunction.apply(key, value);
+        }
+    }
+
+    @Override
+    public V remove(K key) {
+        V result = map.remove(key);
+        if (result != null) {
+            EventuallyConsistentMapEvent<K, V> removeEvent =
+                    new EventuallyConsistentMapEvent<>(mapName, REMOVE,
+                            key, map.get(key));
+            notifyListeners(removeEvent);
+        }
+        return result;
+    }
+
+    @Override
+    public void remove(K key, V value) {
+        boolean removed = map.remove(key, value);
+        if (removed) {
+            EventuallyConsistentMapEvent<K, V> removeEvent =
+                    new EventuallyConsistentMapEvent<>(mapName, REMOVE, key, value);
+            notifyListeners(removeEvent);
+        }
+    }
+
+    @Override
+    public V compute(K key, BiFunction<K, V, V> recomputeFunction) {
+        return map.compute(key, recomputeFunction);
+    }
+
+    @Override
+    public void putAll(Map<? extends K, ? extends V> m) {
+        map.putAll(m);
+    }
+
+    @Override
+    public void clear() {
+        map.clear();
+    }
+
+    @Override
+    public Set<K> keySet() {
+        return map.keySet();
+    }
+
+    @Override
+    public Collection<V> values() {
+        return map.values();
+    }
+
+    @Override
+    public Set<Map.Entry<K, V>> entrySet() {
+        return map.entrySet();
+    }
+
+    public static <K, V> Builder<K, V> builder() {
+        return new Builder<>();
+    }
+
+    @Override
+    public void addListener(EventuallyConsistentMapListener<K, V> listener) {
+        listeners.add(listener);
+    }
+
+    @Override
+    public void removeListener(EventuallyConsistentMapListener<K, V> listener) {
+        listeners.remove(listener);
+    }
+
+    public static class Builder<K, V> implements EventuallyConsistentMapBuilder<K, V> {
+        private String name;
+        private BiFunction<K, V, Collection<NodeId>> peerUpdateFunction;
+
+        @Override
+        public EventuallyConsistentMapBuilder<K, V> withName(String name) {
+            this.name = name;
+            return this;
+        }
+
+        @Override
+        public EventuallyConsistentMapBuilder<K, V> withSerializer(KryoNamespace.Builder serializerBuilder) {
+            return this;
+        }
+
+        @Override
+        public EventuallyConsistentMapBuilder<K, V>
+        withTimestampProvider(BiFunction<K, V, Timestamp> timestampProvider) {
+            return this;
+        }
+
+        @Override
+        public EventuallyConsistentMapBuilder<K, V> withEventExecutor(ExecutorService executor) {
+            return this;
+        }
+
+        @Override
+        public EventuallyConsistentMapBuilder<K, V> withCommunicationExecutor(ExecutorService executor) {
+            return this;
+        }
+
+        @Override
+        public EventuallyConsistentMapBuilder<K, V> withBackgroundExecutor(ScheduledExecutorService executor) {
+            return this;
+        }
+
+        @Override
+        public EventuallyConsistentMapBuilder<K, V>
+        withPeerUpdateFunction(BiFunction<K, V, Collection<NodeId>> peerUpdateFunction) {
+            this.peerUpdateFunction = peerUpdateFunction;
+            return this;
+        }
+
+        @Override
+        public EventuallyConsistentMapBuilder<K, V> withTombstonesDisabled() {
+            return this;
+        }
+
+        @Override
+        public EventuallyConsistentMapBuilder<K, V> withAntiEntropyPeriod(long period, TimeUnit unit) {
+            return this;
+        }
+
+        @Override
+        public EventuallyConsistentMapBuilder<K, V> withFasterConvergence() {
+            return this;
+        }
+
+        @Override
+        public EventuallyConsistentMapBuilder<K, V> withPersistence() {
+            return this;
+        }
+
+        @Override
+        public EventuallyConsistentMap<K, V> build() {
+            if (name == null) {
+                name = "test";
+            }
+            return new VtnEventuallyConsistentMapTest<>(name, peerUpdateFunction);
+        }
+    }
+
+}
+
diff --git a/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnStorageServiceAdapter.java b/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnStorageServiceAdapter.java
index efb1a79..4724ceb 100644
--- a/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnStorageServiceAdapter.java
+++ b/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnStorageServiceAdapter.java
@@ -1,65 +1,65 @@
-/*
- * 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.vtnrsc.util;
-
-import org.onosproject.store.service.EventuallyConsistentMapBuilder;
-import org.onosproject.store.service.ConsistentMapBuilder;
-import org.onosproject.store.service.DistributedSetBuilder;
-import org.onosproject.store.service.DistributedQueueBuilder;
-import org.onosproject.store.service.AtomicCounterBuilder;
-import org.onosproject.store.service.AtomicValueBuilder;
-import org.onosproject.store.service.TransactionContextBuilder;
-import org.onosproject.store.service.StorageService;
-
-/**
- * Adapter for the storage service.
- */
-public class VtnStorageServiceAdapter implements StorageService {
-    @Override
-    public <K, V> EventuallyConsistentMapBuilder<K, V> eventuallyConsistentMapBuilder() {
-        return null;
-    }
-
-    @Override
-    public <K, V> ConsistentMapBuilder<K, V> consistentMapBuilder() {
-        return null;
-    }
-
-    @Override
-    public <E> DistributedSetBuilder<E> setBuilder() {
-        return null;
-    }
-
-    @Override
-    public <E> DistributedQueueBuilder<E> queueBuilder() {
-        return null;
-    }
-
-    @Override
-    public AtomicCounterBuilder atomicCounterBuilder() {
-        return null;
-    }
-
-    @Override
-    public <V> AtomicValueBuilder<V> atomicValueBuilder() {
-        return null;
-    }
-
-    @Override
-    public TransactionContextBuilder transactionContextBuilder() {
-        return null;
-    }
-}
+/*
+ * 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.vtnrsc.util;
+
+import org.onosproject.store.service.EventuallyConsistentMapBuilder;
+import org.onosproject.store.service.ConsistentMapBuilder;
+import org.onosproject.store.service.DistributedSetBuilder;
+import org.onosproject.store.service.DistributedQueueBuilder;
+import org.onosproject.store.service.AtomicCounterBuilder;
+import org.onosproject.store.service.AtomicValueBuilder;
+import org.onosproject.store.service.TransactionContextBuilder;
+import org.onosproject.store.service.StorageService;
+
+/**
+ * Adapter for the storage service.
+ */
+public class VtnStorageServiceAdapter implements StorageService {
+    @Override
+    public <K, V> EventuallyConsistentMapBuilder<K, V> eventuallyConsistentMapBuilder() {
+        return null;
+    }
+
+    @Override
+    public <K, V> ConsistentMapBuilder<K, V> consistentMapBuilder() {
+        return null;
+    }
+
+    @Override
+    public <E> DistributedSetBuilder<E> setBuilder() {
+        return null;
+    }
+
+    @Override
+    public <E> DistributedQueueBuilder<E> queueBuilder() {
+        return null;
+    }
+
+    @Override
+    public AtomicCounterBuilder atomicCounterBuilder() {
+        return null;
+    }
+
+    @Override
+    public <V> AtomicValueBuilder<V> atomicValueBuilder() {
+        return null;
+    }
+
+    @Override
+    public TransactionContextBuilder transactionContextBuilder() {
+        return null;
+    }
+}
diff --git a/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnStorageServiceTest.java b/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnStorageServiceTest.java
index 1f0f183..0537ff5 100644
--- a/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnStorageServiceTest.java
+++ b/apps/vtn/vtnrsc/src/test/java/org/onosproject/vtnrsc/util/VtnStorageServiceTest.java
@@ -1,25 +1,25 @@
-/*
- * 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.vtnrsc.util;
-
-import org.onosproject.store.service.EventuallyConsistentMapBuilder;
-
-public class VtnStorageServiceTest extends VtnStorageServiceAdapter {
-    @Override
-    public <K, V> EventuallyConsistentMapBuilder<K, V> eventuallyConsistentMapBuilder() {
-        return VtnEventuallyConsistentMapTest.builder();
-    }
-}
+/*
+ * 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.vtnrsc.util;
+
+import org.onosproject.store.service.EventuallyConsistentMapBuilder;
+
+public class VtnStorageServiceTest extends VtnStorageServiceAdapter {
+    @Override
+    public <K, V> EventuallyConsistentMapBuilder<K, V> eventuallyConsistentMapBuilder() {
+        return VtnEventuallyConsistentMapTest.builder();
+    }
+}
diff --git a/cli/src/main/java/org/onosproject/cli/net/GetFlowStatistics.java b/cli/src/main/java/org/onosproject/cli/net/GetFlowStatistics.java
index 4bbf4f1..f2e977c 100644
--- a/cli/src/main/java/org/onosproject/cli/net/GetFlowStatistics.java
+++ b/cli/src/main/java/org/onosproject/cli/net/GetFlowStatistics.java
@@ -1,323 +1,323 @@
-/*
- * 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.cli.net;
-
-import org.apache.karaf.shell.commands.Argument;
-import org.apache.karaf.shell.commands.Command;
-import org.apache.karaf.shell.commands.Option;
-import org.onosproject.cli.AbstractShellCommand;
-import org.onosproject.net.ConnectPoint;
-import org.onosproject.net.Device;
-import org.onosproject.net.DeviceId;
-import org.onosproject.net.Port;
-import org.onosproject.net.PortNumber;
-import org.onosproject.net.device.DeviceService;
-import org.onosproject.net.flow.TypedStoredFlowEntry;
-import org.onosproject.net.flow.instructions.Instruction;
-import org.onosproject.net.statistic.FlowStatisticService;
-import org.onosproject.net.statistic.SummaryFlowEntryWithLoad;
-import org.onosproject.net.statistic.TypedFlowEntryWithLoad;
-
-import java.util.List;
-import java.util.Map;
-
-import static org.onosproject.net.DeviceId.deviceId;
-import static org.onosproject.net.PortNumber.portNumber;
-
-/**
- * Fetches flow statistics with a flow type and instruction type.
- */
-@Command(scope = "onos", name = "get-flow-stats",
-        description = "Fetches flow stats for a connection point with given flow type and instruction type")
-public class GetFlowStatistics extends AbstractShellCommand {
-    @Argument(index = 0, name = "devicePort",
-            description = "Device[/Port] connectPoint Description",
-            required = true, multiValued = false)
-    String devicePort = null;
-
-    @Option(name = "-s", aliases = "--summary",
-            description = "Show flow stats summary",
-            required = false, multiValued = false)
-    boolean showSummary = true; // default summary
-
-    @Option(name = "-a", aliases = "--all",
-            description = "Show flow stats all",
-            required = false, multiValued = false)
-    boolean showAll = false;
-
-    @Option(name = "-t", aliases = "--topn",
-            description = "Show flow stats topn",
-            required = false, multiValued = false)
-    String showTopn = null;
-
-    @Option(name = "-f", aliases = "--flowType",
-            description = "Flow live type, It includes IMMEDIATE, SHORT, MID, LONG, UNKNOWN"
-                          + ", and is valid with -a or -t option only",
-            required = false, multiValued = false)
-    String flowLiveType = null;
-
-    @Option(name = "-i", aliases = "--instructionType",
-            description = "Flow instruction type, It includes DROP, OUTPUT, GROUP, L0MODIFICATION, L2MODIFICATION,"
-                    + " TABLE, L3MODIFICATION, METADATA"
-                    + ", and is valid with -a or -t option only",
-            required = false, multiValued = false)
-    String instructionType = null;
-
-    @Override
-    protected void execute() {
-        DeviceService deviceService = get(DeviceService.class);
-        FlowStatisticService flowStatsService = get(FlowStatisticService.class);
-
-        String deviceUri = getDeviceId(devicePort);
-        String portUri = getPortNumber(devicePort);
-
-        DeviceId ingressDeviceId = deviceId(deviceUri);
-        PortNumber ingressPortNumber;
-        if (portUri.length() == 0) {
-            ingressPortNumber = null;
-        } else {
-            ingressPortNumber = portNumber(portUri);
-        }
-
-        Device device = deviceService.getDevice(ingressDeviceId);
-        if (device == null) {
-            error("No such device %s", ingressDeviceId.uri());
-            return;
-        }
-
-        if (ingressPortNumber != null) {
-            Port port = deviceService.getPort(ingressDeviceId, ingressPortNumber);
-            if (port == null) {
-                error("No such port %s on device %s", portUri, ingressDeviceId.uri());
-                return;
-            }
-        }
-
-        if (flowLiveType != null) {
-            flowLiveType = flowLiveType.toUpperCase();
-        }
-        if (instructionType != null) {
-            instructionType = instructionType.toUpperCase();
-        }
-
-        // convert String to FlowLiveType and check validity
-        TypedStoredFlowEntry.FlowLiveType inLiveType;
-        if (flowLiveType == null) {
-            inLiveType = null;
-        } else {
-            inLiveType = getFlowLiveType(flowLiveType);
-            if (inLiveType == null) {
-                error("Invalid flow live type [%s] error", flowLiveType);
-                return;
-            }
-        }
-        // convert String to InstructionType and check validity
-        Instruction.Type inInstructionType;
-        if (instructionType == null) {
-            inInstructionType = null;
-        } else {
-            inInstructionType = getInstructionType(instructionType);
-            if (inInstructionType == null) {
-                error("Invalid instruction type [%s] error", instructionType);
-                return;
-            }
-        }
-
-        if (showTopn != null) {
-            int topn = Integer.parseInt(showTopn);
-
-            if (topn <= 0) {
-                topn = 100; //default value
-            } else if (topn > 1000) {
-                topn = 1000; //max value
-            }
-
-            // print show topn head line with type
-            print("deviceId=%s, show TOPN=%s flows, live type=%s, instruction type=%s",
-                    deviceUri,
-                    Integer.toString(topn),
-                    flowLiveType == null ? "ALL" : flowLiveType,
-                    instructionType == null ? "ALL" : instructionType);
-            if (ingressPortNumber == null) {
-                Map<ConnectPoint, List<TypedFlowEntryWithLoad>> typedFlowLoadMap =
-                          flowStatsService.loadTopnByType(device, inLiveType, inInstructionType, topn);
-                // print all ports topn flows load for a given device
-                for (ConnectPoint cp : typedFlowLoadMap.keySet()) {
-                    printPortFlowsLoad(cp, typedFlowLoadMap.get(cp));
-                }
-            } else {
-                List<TypedFlowEntryWithLoad> typedFlowLoad =
-                        flowStatsService.loadTopnByType(device, ingressPortNumber, inLiveType, inInstructionType, topn);
-                // print device/port topn flows load
-                ConnectPoint cp = new ConnectPoint(ingressDeviceId, ingressPortNumber);
-                printPortFlowsLoad(cp, typedFlowLoad);
-            }
-        } else if (showAll) { // is true?
-            // print show all head line with type
-            print("deviceId=%s, show ALL flows, live type=%s, instruction type=%s",
-                    deviceUri,
-                    flowLiveType == null ? "ALL" : flowLiveType,
-                    instructionType == null ? "ALL" : instructionType);
-            if (ingressPortNumber == null) {
-                Map<ConnectPoint, List<TypedFlowEntryWithLoad>> typedFlowLoadMap =
-                        flowStatsService.loadAllByType(device, inLiveType, inInstructionType);
-                // print all ports all flows load for a given device
-                for (ConnectPoint cp : typedFlowLoadMap.keySet()) {
-                    printPortFlowsLoad(cp, typedFlowLoadMap.get(cp));
-                }
-            } else {
-                List<TypedFlowEntryWithLoad> typedFlowLoad =
-                        flowStatsService.loadAllByType(device, ingressPortNumber, inLiveType, inInstructionType);
-                // print device/port all flows load
-                ConnectPoint cp = new ConnectPoint(ingressDeviceId, ingressPortNumber);
-                printPortFlowsLoad(cp, typedFlowLoad);
-            }
-        } else { // if (showSummary == true) //always is true
-            // print show summary head line
-            print("deviceId=%s, show SUMMARY flows", deviceUri);
-            if (ingressPortNumber == null) {
-                Map<ConnectPoint, SummaryFlowEntryWithLoad> summaryFlowLoadMap =
-                        flowStatsService.loadSummary(device);
-                // print all ports flow load summary for a given device
-                for (ConnectPoint cp : summaryFlowLoadMap.keySet()) {
-                    printPortSummaryLoad(cp, summaryFlowLoadMap.get(cp));
-                }
-            } else {
-                SummaryFlowEntryWithLoad summaryFlowLoad =
-                        flowStatsService.loadSummary(device, ingressPortNumber);
-                // print device/port flow load summary
-                ConnectPoint cp = new ConnectPoint(ingressDeviceId, ingressPortNumber);
-                printPortSummaryLoad(cp, summaryFlowLoad);
-            }
-        }
-    }
-
-    /**
-     * Extracts the port number portion of the ConnectPoint.
-     *
-     * @param deviceString string representing the device/port
-     * @return port number as a string, empty string if the port is not found
-     */
-    private String getPortNumber(String deviceString) {
-        if (deviceString == null) {
-            return "";
-        }
-
-        int slash = deviceString.indexOf('/');
-        if (slash <= 0) {
-            return ""; // return when no port number
-        }
-        return deviceString.substring(slash + 1, deviceString.length());
-    }
-
-    /**
-     * Extracts the device ID portion of the ConnectPoint.
-     *
-     * @param deviceString string representing the device/port
-     * @return device ID string
-     */
-    private String getDeviceId(String deviceString) {
-        if (deviceString == null) {
-            return "";
-        }
-
-        int slash = deviceString.indexOf('/');
-        if (slash <= 0) {
-            return deviceString; // return only included device ID
-        }
-        return deviceString.substring(0, slash);
-    }
-
-    /**
-     * converts string of flow live type to FloeLiveType enum.
-     *
-     * @param liveType string representing the flow live type
-     * @return TypedStoredFlowEntry.FlowLiveType
-     */
-    private TypedStoredFlowEntry.FlowLiveType getFlowLiveType(String liveType) {
-        String liveTypeUC = liveType.toUpperCase();
-
-        if (liveTypeUC.equals("IMMEDIATE")) {
-            return TypedStoredFlowEntry.FlowLiveType.IMMEDIATE_FLOW;
-        } else if (liveTypeUC.equals("SHORT")) {
-            return TypedStoredFlowEntry.FlowLiveType.SHORT_FLOW;
-        } else if (liveTypeUC.equals("MID")) {
-            return TypedStoredFlowEntry.FlowLiveType.MID_FLOW;
-        } else if (liveTypeUC.equals("LONG")) {
-            return TypedStoredFlowEntry.FlowLiveType.LONG_FLOW;
-        } else if (liveTypeUC.equals("UNKNOWN")) {
-            return TypedStoredFlowEntry.FlowLiveType.UNKNOWN_FLOW;
-        } else {
-            return null; // flow live type error
-        }
-    }
-
-    /**
-     * converts string of instruction type to Instruction type enum.
-     *
-     * @param instType string representing the instruction type
-     * @return Instruction.Type
-     */
-    private Instruction.Type getInstructionType(String instType) {
-        String instTypeUC = instType.toUpperCase();
-
-        if (instTypeUC.equals("DROP")) {
-            return Instruction.Type.DROP;
-        } else if (instTypeUC.equals("OUTPUT")) {
-            return Instruction.Type.OUTPUT;
-        } else if (instTypeUC.equals("GROUP")) {
-            return Instruction.Type.GROUP;
-        } else if (instTypeUC.equals("L0MODIFICATION")) {
-            return Instruction.Type.L0MODIFICATION;
-        } else if (instTypeUC.equals("L2MODIFICATION")) {
-            return Instruction.Type.L2MODIFICATION;
-        } else if (instTypeUC.equals("TABLE")) {
-            return Instruction.Type.TABLE;
-        } else if (instTypeUC.equals("L3MODIFICATION")) {
-            return Instruction.Type.L3MODIFICATION;
-        } else if (instTypeUC.equals("METADATA")) {
-            return Instruction.Type.METADATA;
-        } else {
-             return null; // instruction type error
-        }
-    }
-
-    private void printPortFlowsLoad(ConnectPoint cp, List<TypedFlowEntryWithLoad> typedFlowLoad) {
-       print("  deviceId/Port=%s/%s, %s flows", cp.elementId(), cp.port(), typedFlowLoad.size());
-        for (TypedFlowEntryWithLoad tfel: typedFlowLoad) {
-            TypedStoredFlowEntry tfe =  tfel.typedStoredFlowEntry();
-            print("    flowId=%s, state=%s, liveType=%s, life=%s -> %s",
-                    Long.toHexString(tfe.id().value()),
-                    tfe.state(),
-                    tfe.flowLiveType(),
-                    tfe.life(),
-                    tfel.load().isValid() ? tfel.load() : "Load{rate=0, NOT VALID}");
-        }
-    }
-
-    private void printPortSummaryLoad(ConnectPoint cp, SummaryFlowEntryWithLoad summaryFlowLoad) {
-        print("  deviceId/Port=%s/%s, Total=%s, Immediate=%s, Short=%s, Mid=%s, Long=%s, Unknown=%s",
-                cp.elementId(),
-                cp.port(),
-                summaryFlowLoad.totalLoad().isValid() ? summaryFlowLoad.totalLoad() : "Load{rate=0, NOT VALID}",
-                summaryFlowLoad.immediateLoad().isValid() ? summaryFlowLoad.immediateLoad() : "Load{rate=0, NOT VALID}",
-                summaryFlowLoad.shortLoad().isValid() ? summaryFlowLoad.shortLoad() : "Load{rate=0, NOT VALID}",
-                summaryFlowLoad.midLoad().isValid() ? summaryFlowLoad.midLoad() : "Load{rate=0, NOT VALID}",
-                summaryFlowLoad.longLoad().isValid() ? summaryFlowLoad.longLoad() : "Load{rate=0, NOT VALID}",
-                summaryFlowLoad.unknownLoad().isValid() ? summaryFlowLoad.unknownLoad() : "Load{rate=0, NOT VALID}");
-    }
-}
+/*
+ * 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.cli.net;
+
+import org.apache.karaf.shell.commands.Argument;
+import org.apache.karaf.shell.commands.Command;
+import org.apache.karaf.shell.commands.Option;
+import org.onosproject.cli.AbstractShellCommand;
+import org.onosproject.net.ConnectPoint;
+import org.onosproject.net.Device;
+import org.onosproject.net.DeviceId;
+import org.onosproject.net.Port;
+import org.onosproject.net.PortNumber;
+import org.onosproject.net.device.DeviceService;
+import org.onosproject.net.flow.TypedStoredFlowEntry;
+import org.onosproject.net.flow.instructions.Instruction;
+import org.onosproject.net.statistic.FlowStatisticService;
+import org.onosproject.net.statistic.SummaryFlowEntryWithLoad;
+import org.onosproject.net.statistic.TypedFlowEntryWithLoad;
+
+import java.util.List;
+import java.util.Map;
+
+import static org.onosproject.net.DeviceId.deviceId;
+import static org.onosproject.net.PortNumber.portNumber;
+
+/**
+ * Fetches flow statistics with a flow type and instruction type.
+ */
+@Command(scope = "onos", name = "get-flow-stats",
+        description = "Fetches flow stats for a connection point with given flow type and instruction type")
+public class GetFlowStatistics extends AbstractShellCommand {
+    @Argument(index = 0, name = "devicePort",
+            description = "Device[/Port] connectPoint Description",
+            required = true, multiValued = false)
+    String devicePort = null;
+
+    @Option(name = "-s", aliases = "--summary",
+            description = "Show flow stats summary",
+            required = false, multiValued = false)
+    boolean showSummary = true; // default summary
+
+    @Option(name = "-a", aliases = "--all",
+            description = "Show flow stats all",
+            required = false, multiValued = false)
+    boolean showAll = false;
+
+    @Option(name = "-t", aliases = "--topn",
+            description = "Show flow stats topn",
+            required = false, multiValued = false)
+    String showTopn = null;
+
+    @Option(name = "-f", aliases = "--flowType",
+            description = "Flow live type, It includes IMMEDIATE, SHORT, MID, LONG, UNKNOWN"
+                          + ", and is valid with -a or -t option only",
+            required = false, multiValued = false)
+    String flowLiveType = null;
+
+    @Option(name = "-i", aliases = "--instructionType",
+            description = "Flow instruction type, It includes DROP, OUTPUT, GROUP, L0MODIFICATION, L2MODIFICATION,"
+                    + " TABLE, L3MODIFICATION, METADATA"
+                    + ", and is valid with -a or -t option only",
+            required = false, multiValued = false)
+    String instructionType = null;
+
+    @Override
+    protected void execute() {
+        DeviceService deviceService = get(DeviceService.class);
+        FlowStatisticService flowStatsService = get(FlowStatisticService.class);
+
+        String deviceUri = getDeviceId(devicePort);
+        String portUri = getPortNumber(devicePort);
+
+        DeviceId ingressDeviceId = deviceId(deviceUri);
+        PortNumber ingressPortNumber;
+        if (portUri.length() == 0) {
+            ingressPortNumber = null;
+        } else {
+            ingressPortNumber = portNumber(portUri);
+        }
+
+        Device device = deviceService.getDevice(ingressDeviceId);
+        if (device == null) {
+            error("No such device %s", ingressDeviceId.uri());
+            return;
+        }
+
+        if (ingressPortNumber != null) {
+            Port port = deviceService.getPort(ingressDeviceId, ingressPortNumber);
+            if (port == null) {
+                error("No such port %s on device %s", portUri, ingressDeviceId.uri());
+                return;
+            }
+        }
+
+        if (flowLiveType != null) {
+            flowLiveType = flowLiveType.toUpperCase();
+        }
+        if (instructionType != null) {
+            instructionType = instructionType.toUpperCase();
+        }
+
+        // convert String to FlowLiveType and check validity
+        TypedStoredFlowEntry.FlowLiveType inLiveType;
+        if (flowLiveType == null) {
+            inLiveType = null;
+        } else {
+            inLiveType = getFlowLiveType(flowLiveType);
+            if (inLiveType == null) {
+                error("Invalid flow live type [%s] error", flowLiveType);
+                return;
+            }
+        }
+        // convert String to InstructionType and check validity
+        Instruction.Type inInstructionType;
+        if (instructionType == null) {
+            inInstructionType = null;
+        } else {
+            inInstructionType = getInstructionType(instructionType);
+            if (inInstructionType == null) {
+                error("Invalid instruction type [%s] error", instructionType);
+                return;
+            }
+        }
+
+        if (showTopn != null) {
+            int topn = Integer.parseInt(showTopn);
+
+            if (topn <= 0) {
+                topn = 100; //default value
+            } else if (topn > 1000) {
+                topn = 1000; //max value
+            }
+
+            // print show topn head line with type
+            print("deviceId=%s, show TOPN=%s flows, live type=%s, instruction type=%s",
+                    deviceUri,
+                    Integer.toString(topn),
+                    flowLiveType == null ? "ALL" : flowLiveType,
+                    instructionType == null ? "ALL" : instructionType);
+            if (ingressPortNumber == null) {
+                Map<ConnectPoint, List<TypedFlowEntryWithLoad>> typedFlowLoadMap =
+                          flowStatsService.loadTopnByType(device, inLiveType, inInstructionType, topn);
+                // print all ports topn flows load for a given device
+                for (ConnectPoint cp : typedFlowLoadMap.keySet()) {
+                    printPortFlowsLoad(cp, typedFlowLoadMap.get(cp));
+                }
+            } else {
+                List<TypedFlowEntryWithLoad> typedFlowLoad =
+                        flowStatsService.loadTopnByType(device, ingressPortNumber, inLiveType, inInstructionType, topn);
+                // print device/port topn flows load
+                ConnectPoint cp = new ConnectPoint(ingressDeviceId, ingressPortNumber);
+                printPortFlowsLoad(cp, typedFlowLoad);
+            }
+        } else if (showAll) { // is true?
+            // print show all head line with type
+            print("deviceId=%s, show ALL flows, live type=%s, instruction type=%s",
+                    deviceUri,
+                    flowLiveType == null ? "ALL" : flowLiveType,
+                    instructionType == null ? "ALL" : instructionType);
+            if (ingressPortNumber == null) {
+                Map<ConnectPoint, List<TypedFlowEntryWithLoad>> typedFlowLoadMap =
+                        flowStatsService.loadAllByType(device, inLiveType, inInstructionType);
+                // print all ports all flows load for a given device
+                for (ConnectPoint cp : typedFlowLoadMap.keySet()) {
+                    printPortFlowsLoad(cp, typedFlowLoadMap.get(cp));
+                }
+            } else {
+                List<TypedFlowEntryWithLoad> typedFlowLoad =
+                        flowStatsService.loadAllByType(device, ingressPortNumber, inLiveType, inInstructionType);
+                // print device/port all flows load
+                ConnectPoint cp = new ConnectPoint(ingressDeviceId, ingressPortNumber);
+                printPortFlowsLoad(cp, typedFlowLoad);
+            }
+        } else { // if (showSummary == true) //always is true
+            // print show summary head line
+            print("deviceId=%s, show SUMMARY flows", deviceUri);
+            if (ingressPortNumber == null) {
+                Map<ConnectPoint, SummaryFlowEntryWithLoad> summaryFlowLoadMap =
+                        flowStatsService.loadSummary(device);
+                // print all ports flow load summary for a given device
+                for (ConnectPoint cp : summaryFlowLoadMap.keySet()) {
+                    printPortSummaryLoad(cp, summaryFlowLoadMap.get(cp));
+                }
+            } else {
+                SummaryFlowEntryWithLoad summaryFlowLoad =
+                        flowStatsService.loadSummary(device, ingressPortNumber);
+                // print device/port flow load summary
+                ConnectPoint cp = new ConnectPoint(ingressDeviceId, ingressPortNumber);
+                printPortSummaryLoad(cp, summaryFlowLoad);
+            }
+        }
+    }
+
+    /**
+     * Extracts the port number portion of the ConnectPoint.
+     *
+     * @param deviceString string representing the device/port
+     * @return port number as a string, empty string if the port is not found
+     */
+    private String getPortNumber(String deviceString) {
+        if (deviceString == null) {
+            return "";
+        }
+
+        int slash = deviceString.indexOf('/');
+        if (slash <= 0) {
+            return ""; // return when no port number
+        }
+        return deviceString.substring(slash + 1, deviceString.length());
+    }
+
+    /**
+     * Extracts the device ID portion of the ConnectPoint.
+     *
+     * @param deviceString string representing the device/port
+     * @return device ID string
+     */
+    private String getDeviceId(String deviceString) {
+        if (deviceString == null) {
+            return "";
+        }
+
+        int slash = deviceString.indexOf('/');
+        if (slash <= 0) {
+            return deviceString; // return only included device ID
+        }
+        return deviceString.substring(0, slash);
+    }
+
+    /**
+     * converts string of flow live type to FloeLiveType enum.
+     *
+     * @param liveType string representing the flow live type
+     * @return TypedStoredFlowEntry.FlowLiveType
+     */
+    private TypedStoredFlowEntry.FlowLiveType getFlowLiveType(String liveType) {
+        String liveTypeUC = liveType.toUpperCase();
+
+        if (liveTypeUC.equals("IMMEDIATE")) {
+            return TypedStoredFlowEntry.FlowLiveType.IMMEDIATE_FLOW;
+        } else if (liveTypeUC.equals("SHORT")) {
+            return TypedStoredFlowEntry.FlowLiveType.SHORT_FLOW;
+        } else if (liveTypeUC.equals("MID")) {
+            return TypedStoredFlowEntry.FlowLiveType.MID_FLOW;
+        } else if (liveTypeUC.equals("LONG")) {
+            return TypedStoredFlowEntry.FlowLiveType.LONG_FLOW;
+        } else if (liveTypeUC.equals("UNKNOWN")) {
+            return TypedStoredFlowEntry.FlowLiveType.UNKNOWN_FLOW;
+        } else {
+            return null; // flow live type error
+        }
+    }
+
+    /**
+     * converts string of instruction type to Instruction type enum.
+     *
+     * @param instType string representing the instruction type
+     * @return Instruction.Type
+     */
+    private Instruction.Type getInstructionType(String instType) {
+        String instTypeUC = instType.toUpperCase();
+
+        if (instTypeUC.equals("DROP")) {
+            return Instruction.Type.DROP;
+        } else if (instTypeUC.equals("OUTPUT")) {
+            return Instruction.Type.OUTPUT;
+        } else if (instTypeUC.equals("GROUP")) {
+            return Instruction.Type.GROUP;
+        } else if (instTypeUC.equals("L0MODIFICATION")) {
+            return Instruction.Type.L0MODIFICATION;
+        } else if (instTypeUC.equals("L2MODIFICATION")) {
+            return Instruction.Type.L2MODIFICATION;
+        } else if (instTypeUC.equals("TABLE")) {
+            return Instruction.Type.TABLE;
+        } else if (instTypeUC.equals("L3MODIFICATION")) {
+            return Instruction.Type.L3MODIFICATION;
+        } else if (instTypeUC.equals("METADATA")) {
+            return Instruction.Type.METADATA;
+        } else {
+             return null; // instruction type error
+        }
+    }
+
+    private void printPortFlowsLoad(ConnectPoint cp, List<TypedFlowEntryWithLoad> typedFlowLoad) {
+       print("  deviceId/Port=%s/%s, %s flows", cp.elementId(), cp.port(), typedFlowLoad.size());
+        for (TypedFlowEntryWithLoad tfel: typedFlowLoad) {
+            TypedStoredFlowEntry tfe =  tfel.typedStoredFlowEntry();
+            print("    flowId=%s, state=%s, liveType=%s, life=%s -> %s",
+                    Long.toHexString(tfe.id().value()),
+                    tfe.state(),
+                    tfe.flowLiveType(),
+                    tfe.life(),
+                    tfel.load().isValid() ? tfel.load() : "Load{rate=0, NOT VALID}");
+        }
+    }
+
+    private void printPortSummaryLoad(ConnectPoint cp, SummaryFlowEntryWithLoad summaryFlowLoad) {
+        print("  deviceId/Port=%s/%s, Total=%s, Immediate=%s, Short=%s, Mid=%s, Long=%s, Unknown=%s",
+                cp.elementId(),
+                cp.port(),
+                summaryFlowLoad.totalLoad().isValid() ? summaryFlowLoad.totalLoad() : "Load{rate=0, NOT VALID}",
+                summaryFlowLoad.immediateLoad().isValid() ? summaryFlowLoad.immediateLoad() : "Load{rate=0, NOT VALID}",
+                summaryFlowLoad.shortLoad().isValid() ? summaryFlowLoad.shortLoad() : "Load{rate=0, NOT VALID}",
+                summaryFlowLoad.midLoad().isValid() ? summaryFlowLoad.midLoad() : "Load{rate=0, NOT VALID}",
+                summaryFlowLoad.longLoad().isValid() ? summaryFlowLoad.longLoad() : "Load{rate=0, NOT VALID}",
+                summaryFlowLoad.unknownLoad().isValid() ? summaryFlowLoad.unknownLoad() : "Load{rate=0, NOT VALID}");
+    }
+}
diff --git a/core/api/src/main/java/org/onosproject/net/flow/DefaultTypedFlowEntry.java b/core/api/src/main/java/org/onosproject/net/flow/DefaultTypedFlowEntry.java
index afceb14..43a32de 100644
--- a/core/api/src/main/java/org/onosproject/net/flow/DefaultTypedFlowEntry.java
+++ b/core/api/src/main/java/org/onosproject/net/flow/DefaultTypedFlowEntry.java
@@ -1,122 +1,122 @@
-/*
- * 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.net.flow;
-
-import static com.google.common.base.MoreObjects.toStringHelper;
-
-/**
- * Default flow entry class with FlowLiveType value, IMMEDIATE_FLOW, SHORT_FLOW, MID_FLOW, LONG_FLOW.
- */
-public class DefaultTypedFlowEntry extends DefaultFlowEntry
-    implements TypedStoredFlowEntry {
-    private FlowLiveType liveType;
-
-    /**
-     * Creates a typed flow entry from flow rule and its statistics, with default flow live type(IMMEDIATE_FLOW).
-     *
-     * @param rule the flow rule
-     * @param state the flow state
-     * @param life the flow duration since creation
-     * @param packets the flow packets count
-     * @param bytes the flow bytes count
-     *
-     */
-    public DefaultTypedFlowEntry(FlowRule rule, FlowEntryState state,
-                            long life, long packets, long bytes) {
-        super(rule, state, life, packets, bytes);
-        this.liveType = FlowLiveType.IMMEDIATE_FLOW;
-    }
-
-    /**
-     * Creates a typed flow entry from flow rule,  with default flow live type(IMMEDIATE_FLOW).
-     *
-     * @param rule the flow rule
-     *
-     */
-    public DefaultTypedFlowEntry(FlowRule rule) {
-        super(rule);
-        this.liveType = FlowLiveType.IMMEDIATE_FLOW;
-    }
-
-    /**
-     * Creates a typed flow entry from flow entry,  with default flow live type(IMMEDIATE_FLOW).
-     *
-     * @param fe the flow entry
-     *
-     */
-    public DefaultTypedFlowEntry(FlowEntry fe) {
-        super(fe, fe.state(), fe.life(), fe.packets(), fe.bytes());
-        this.liveType = FlowLiveType.IMMEDIATE_FLOW;
-    }
-
-    /**
-     * Creates a typed flow entry from flow rule and flow live type.
-     *
-     * @param rule the flow rule
-     * @param liveType the flow live type
-     *
-     */
-    public DefaultTypedFlowEntry(FlowRule rule, FlowLiveType liveType) {
-        super(rule);
-        this.liveType = liveType;
-    }
-
-    /**
-     * Creates a typed flow entry from flow entry and flow live type.
-     *
-     * @param fe the flow rule
-     * @param liveType the flow live type
-     *
-     */
-    public DefaultTypedFlowEntry(FlowEntry fe,  FlowLiveType liveType) {
-        super(fe, fe.state(), fe.life(), fe.packets(), fe.bytes());
-        this.liveType = liveType;
-    }
-
-    /**
-     * Creates a typed flow entry from flow rule, error code and flow live type.
-     *
-     * @param rule the flow rule
-     * @param errType the flow error type
-     * @param errCode the flow error code
-     * @param liveType the flow live type
-     *
-     */
-    public DefaultTypedFlowEntry(FlowRule rule, int errType, int errCode, FlowLiveType liveType) {
-        super(rule, errType, errCode);
-        this.liveType = liveType;
-    }
-
-    @Override
-    public FlowLiveType flowLiveType() {
-        return this.liveType;
-    }
-
-    @Override
-    public void setFlowLiveType(FlowLiveType liveType) {
-        this.liveType = liveType;
-    }
-
-    @Override
-    public String toString() {
-        return toStringHelper(this)
-                .add("entry", super.toString())
-                .add("type", liveType)
-                .toString();
-    }
-}
-
+/*
+ * 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.net.flow;
+
+import static com.google.common.base.MoreObjects.toStringHelper;
+
+/**
+ * Default flow entry class with FlowLiveType value, IMMEDIATE_FLOW, SHORT_FLOW, MID_FLOW, LONG_FLOW.
+ */
+public class DefaultTypedFlowEntry extends DefaultFlowEntry
+    implements TypedStoredFlowEntry {
+    private FlowLiveType liveType;
+
+    /**
+     * Creates a typed flow entry from flow rule and its statistics, with default flow live type(IMMEDIATE_FLOW).
+     *
+     * @param rule the flow rule
+     * @param state the flow state
+     * @param life the flow duration since creation
+     * @param packets the flow packets count
+     * @param bytes the flow bytes count
+     *
+     */
+    public DefaultTypedFlowEntry(FlowRule rule, FlowEntryState state,
+                            long life, long packets, long bytes) {
+        super(rule, state, life, packets, bytes);
+        this.liveType = FlowLiveType.IMMEDIATE_FLOW;
+    }
+
+    /**
+     * Creates a typed flow entry from flow rule,  with default flow live type(IMMEDIATE_FLOW).
+     *
+     * @param rule the flow rule
+     *
+     */
+    public DefaultTypedFlowEntry(FlowRule rule) {
+        super(rule);
+        this.liveType = FlowLiveType.IMMEDIATE_FLOW;
+    }
+
+    /**
+     * Creates a typed flow entry from flow entry,  with default flow live type(IMMEDIATE_FLOW).
+     *
+     * @param fe the flow entry
+     *
+     */
+    public DefaultTypedFlowEntry(FlowEntry fe) {
+        super(fe, fe.state(), fe.life(), fe.packets(), fe.bytes());
+        this.liveType = FlowLiveType.IMMEDIATE_FLOW;
+    }
+
+    /**
+     * Creates a typed flow entry from flow rule and flow live type.
+     *
+     * @param rule the flow rule
+     * @param liveType the flow live type
+     *
+     */
+    public DefaultTypedFlowEntry(FlowRule rule, FlowLiveType liveType) {
+        super(rule);
+        this.liveType = liveType;
+    }
+
+    /**
+     * Creates a typed flow entry from flow entry and flow live type.
+     *
+     * @param fe the flow rule
+     * @param liveType the flow live type
+     *
+     */
+    public DefaultTypedFlowEntry(FlowEntry fe,  FlowLiveType liveType) {
+        super(fe, fe.state(), fe.life(), fe.packets(), fe.bytes());
+        this.liveType = liveType;
+    }
+
+    /**
+     * Creates a typed flow entry from flow rule, error code and flow live type.
+     *
+     * @param rule the flow rule
+     * @param errType the flow error type
+     * @param errCode the flow error code
+     * @param liveType the flow live type
+     *
+     */
+    public DefaultTypedFlowEntry(FlowRule rule, int errType, int errCode, FlowLiveType liveType) {
+        super(rule, errType, errCode);
+        this.liveType = liveType;
+    }
+
+    @Override
+    public FlowLiveType flowLiveType() {
+        return this.liveType;
+    }
+
+    @Override
+    public void setFlowLiveType(FlowLiveType liveType) {
+        this.liveType = liveType;
+    }
+
+    @Override
+    public String toString() {
+        return toStringHelper(this)
+                .add("entry", super.toString())
+                .add("type", liveType)
+                .toString();
+    }
+}
+
diff --git a/core/api/src/main/java/org/onosproject/net/flow/TypedStoredFlowEntry.java b/core/api/src/main/java/org/onosproject/net/flow/TypedStoredFlowEntry.java
index 965fd1f..8cdfae7 100644
--- a/core/api/src/main/java/org/onosproject/net/flow/TypedStoredFlowEntry.java
+++ b/core/api/src/main/java/org/onosproject/net/flow/TypedStoredFlowEntry.java
@@ -1,67 +1,67 @@
-/*
- * 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.net.flow;
-
-/**
- * Represents a flow live type for a given flow entry.
- */
-public interface TypedStoredFlowEntry extends StoredFlowEntry {
-    enum FlowLiveType {
-        /**
-         * Indicates that this rule has been submitted for addition immediately.
-         * Not necessarily collecting flow stats.
-         */
-        IMMEDIATE_FLOW,
-
-        /**
-         * Indicates that this rule has been submitted for a short time.
-         * Necessarily collecting flow stats every calAndPollInterval.
-         */
-        SHORT_FLOW,
-
-        /**
-         * Indicates that this rule has been submitted for a mid time.
-         * Necessarily collecting flow stats every midPollInterval.
-         */
-        MID_FLOW,
-
-        /**
-         * Indicates that this rule has been submitted for a long time.
-         * Necessarily collecting flow stats every longPollInterval.
-         */
-        LONG_FLOW,
-
-        /**
-         * Indicates that this rule has been submitted for UNKNOWN or ERROR.
-         * Not necessarily collecting flow stats.
-         */
-        UNKNOWN_FLOW
-    }
-
-    /**
-     * Gets the flow live type for this entry.
-     *
-     * @return flow live type
-     */
-    FlowLiveType flowLiveType();
-
-    /**
-     * Sets the new flow live type for this entry.
-     * @param liveType new flow live type.
-     */
-    void setFlowLiveType(FlowLiveType liveType);
-}
+/*
+ * 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.net.flow;
+
+/**
+ * Represents a flow live type for a given flow entry.
+ */
+public interface TypedStoredFlowEntry extends StoredFlowEntry {
+    enum FlowLiveType {
+        /**
+         * Indicates that this rule has been submitted for addition immediately.
+         * Not necessarily collecting flow stats.
+         */
+        IMMEDIATE_FLOW,
+
+        /**
+         * Indicates that this rule has been submitted for a short time.
+         * Necessarily collecting flow stats every calAndPollInterval.
+         */
+        SHORT_FLOW,
+
+        /**
+         * Indicates that this rule has been submitted for a mid time.
+         * Necessarily collecting flow stats every midPollInterval.
+         */
+        MID_FLOW,
+
+        /**
+         * Indicates that this rule has been submitted for a long time.
+         * Necessarily collecting flow stats every longPollInterval.
+         */
+        LONG_FLOW,
+
+        /**
+         * Indicates that this rule has been submitted for UNKNOWN or ERROR.
+         * Not necessarily collecting flow stats.
+         */
+        UNKNOWN_FLOW
+    }
+
+    /**
+     * Gets the flow live type for this entry.
+     *
+     * @return flow live type
+     */
+    FlowLiveType flowLiveType();
+
+    /**
+     * Sets the new flow live type for this entry.
+     * @param liveType new flow live type.
+     */
+    void setFlowLiveType(FlowLiveType liveType);
+}
diff --git a/core/api/src/main/java/org/onosproject/net/statistic/FlowStatisticService.java b/core/api/src/main/java/org/onosproject/net/statistic/FlowStatisticService.java
index 5216839..544364d 100644
--- a/core/api/src/main/java/org/onosproject/net/statistic/FlowStatisticService.java
+++ b/core/api/src/main/java/org/onosproject/net/statistic/FlowStatisticService.java
@@ -1,106 +1,106 @@
-/*
- * 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.net.statistic;
-
-import org.onosproject.net.ConnectPoint;
-import org.onosproject.net.Device;
-import org.onosproject.net.PortNumber;
-import org.onosproject.net.flow.TypedStoredFlowEntry;
-import org.onosproject.net.flow.instructions.Instruction;
-
-import java.util.List;
-import java.util.Map;
-
-/**
- * Service for obtaining individual flow statistic information about device and link in the system.
- * Basic statistics are obtained from the StatisticService
- */
-public interface FlowStatisticService {
-
-    /**
-     * Obtain the summary load list for the device with the given link.
-     *
-     * @param device the Device  to query.
-     * @return map of summary flow entry load
-     */
-    Map<ConnectPoint, SummaryFlowEntryWithLoad> loadSummary(Device device);
-
-    /**
-     * Obtain the summary load for the device with the given link or port.
-     *
-     * @param device the Device to query.
-     * @param pNumber the port number to query.
-     * @return summary flow entry load
-     */
-    SummaryFlowEntryWithLoad loadSummary(Device device, PortNumber pNumber);
-
-    /**
-     * Obtain the set of the flow type and load list for the device with the given link.
-     *
-     * @param device the Device  to query.
-     * @param liveType the FlowLiveType  to filter, null means no filtering .
-     * @param instType the InstructionType to filter, null means no filtering.
-     * @return map of flow entry load
-     */
-    Map<ConnectPoint, List<TypedFlowEntryWithLoad>> loadAllByType(Device device,
-                                                                  TypedStoredFlowEntry.FlowLiveType liveType,
-                                                                  Instruction.Type instType);
-
-    /**
-     * Obtain the flow type and load list for the device with the given link or port.
-     *
-     * @param device the Device to query.
-     * @param pNumber the port number of the Device to query
-     * @param liveType the FlowLiveType  to filter, null means no filtering .
-     * @param instType the InstructionType to filter, null means no filtering.
-     * @return list of flow entry load
-     */
-    List<TypedFlowEntryWithLoad> loadAllByType(Device device, PortNumber pNumber,
-                                               TypedStoredFlowEntry.FlowLiveType liveType,
-                                               Instruction.Type instType);
-
-    /**
-     * Obtain the set of the flow type and load topn list for the device with the given link.
-     *
-     * @param device the Device  to query.
-     * @param liveType the FlowLiveType  to filter, null means no filtering .
-     * @param instType the InstructionType to filter, null means no filtering.
-     * @param topn the top number to filter, null means no filtering.
-     * @return map of flow entry load
-     */
-    Map<ConnectPoint, List<TypedFlowEntryWithLoad>> loadTopnByType(Device device,
-                                                                   TypedStoredFlowEntry.FlowLiveType liveType,
-                                                                   Instruction.Type instType,
-                                                                   int topn);
-
-    /**
-     * Obtain the flow type and load topn list for the device with the given link or port.
-     *
-     * @param device the Device  to query.
-     * @param pNumber the port number of the Device to query
-     * @param liveType the FlowLiveType  to filter, null means no filtering .
-     * @param instType the InstructionType to filter, null means no filtering.
-     * @param topn topn //FIXME what?
-     * @return list of flow entry load
-     */
-    List<TypedFlowEntryWithLoad> loadTopnByType(Device device, PortNumber pNumber,
-                                                TypedStoredFlowEntry.FlowLiveType liveType,
-                                                Instruction.Type instType,
-                                                int topn);
-}
-
-
+/*
+ * 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.net.statistic;
+
+import org.onosproject.net.ConnectPoint;
+import org.onosproject.net.Device;
+import org.onosproject.net.PortNumber;
+import org.onosproject.net.flow.TypedStoredFlowEntry;
+import org.onosproject.net.flow.instructions.Instruction;
+
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Service for obtaining individual flow statistic information about device and link in the system.
+ * Basic statistics are obtained from the StatisticService
+ */
+public interface FlowStatisticService {
+
+    /**
+     * Obtain the summary load list for the device with the given link.
+     *
+     * @param device the Device  to query.
+     * @return map of summary flow entry load
+     */
+    Map<ConnectPoint, SummaryFlowEntryWithLoad> loadSummary(Device device);
+
+    /**
+     * Obtain the summary load for the device with the given link or port.
+     *
+     * @param device the Device to query.
+     * @param pNumber the port number to query.
+     * @return summary flow entry load
+     */
+    SummaryFlowEntryWithLoad loadSummary(Device device, PortNumber pNumber);
+
+    /**
+     * Obtain the set of the flow type and load list for the device with the given link.
+     *
+     * @param device the Device  to query.
+     * @param liveType the FlowLiveType  to filter, null means no filtering .
+     * @param instType the InstructionType to filter, null means no filtering.
+     * @return map of flow entry load
+     */
+    Map<ConnectPoint, List<TypedFlowEntryWithLoad>> loadAllByType(Device device,
+                                                                  TypedStoredFlowEntry.FlowLiveType liveType,
+                                                                  Instruction.Type instType);
+
+    /**
+     * Obtain the flow type and load list for the device with the given link or port.
+     *
+     * @param device the Device to query.
+     * @param pNumber the port number of the Device to query
+     * @param liveType the FlowLiveType  to filter, null means no filtering .
+     * @param instType the InstructionType to filter, null means no filtering.
+     * @return list of flow entry load
+     */
+    List<TypedFlowEntryWithLoad> loadAllByType(Device device, PortNumber pNumber,
+                                               TypedStoredFlowEntry.FlowLiveType liveType,
+                                               Instruction.Type instType);
+
+    /**
+     * Obtain the set of the flow type and load topn list for the device with the given link.
+     *
+     * @param device the Device  to query.
+     * @param liveType the FlowLiveType  to filter, null means no filtering .
+     * @param instType the InstructionType to filter, null means no filtering.
+     * @param topn the top number to filter, null means no filtering.
+     * @return map of flow entry load
+     */
+    Map<ConnectPoint, List<TypedFlowEntryWithLoad>> loadTopnByType(Device device,
+                                                                   TypedStoredFlowEntry.FlowLiveType liveType,
+                                                                   Instruction.Type instType,
+                                                                   int topn);
+
+    /**
+     * Obtain the flow type and load topn list for the device with the given link or port.
+     *
+     * @param device the Device  to query.
+     * @param pNumber the port number of the Device to query
+     * @param liveType the FlowLiveType  to filter, null means no filtering .
+     * @param instType the InstructionType to filter, null means no filtering.
+     * @param topn topn //FIXME what?
+     * @return list of flow entry load
+     */
+    List<TypedFlowEntryWithLoad> loadTopnByType(Device device, PortNumber pNumber,
+                                                TypedStoredFlowEntry.FlowLiveType liveType,
+                                                Instruction.Type instType,
+                                                int topn);
+}
+
+
diff --git a/core/api/src/main/java/org/onosproject/net/statistic/FlowStatisticStore.java b/core/api/src/main/java/org/onosproject/net/statistic/FlowStatisticStore.java
index 3c2aa89..a27e167 100644
--- a/core/api/src/main/java/org/onosproject/net/statistic/FlowStatisticStore.java
+++ b/core/api/src/main/java/org/onosproject/net/statistic/FlowStatisticStore.java
@@ -1,65 +1,65 @@
-/*
- * 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.net.statistic;
-
-import org.onosproject.net.ConnectPoint;
-import org.onosproject.net.flow.FlowEntry;
-import org.onosproject.net.flow.FlowRule;
-
-import java.util.Set;
-
-/**
- * Flow Store to house the computed statistics.
- */
-public interface FlowStatisticStore {
-    /**
-     * Remove entries associated with this rule.
-     *
-     * @param rule {@link org.onosproject.net.flow.FlowRule}
-     */
-    void removeFlowStatistic(FlowRule rule);
-
-    /**
-     * Adds a flow stats observation for a flow rule. The previous flow will be removed.
-     *
-     * @param rule a {@link org.onosproject.net.flow.FlowEntry}
-     */
-    void addFlowStatistic(FlowEntry rule);
-
-    /**
-     * Updates a stats observation for a flow rule. The old flow stats will be moved to previous stats.
-     *
-     * @param rule a {@link org.onosproject.net.flow.FlowEntry}
-     */
-    void updateFlowStatistic(FlowEntry rule);
-
-    /**
-     * Fetches the current observed flow stats values.
-     *
-     * @param connectPoint the port to fetch information for
-     * @return set of current flow rules
-     */
-    Set<FlowEntry> getCurrentFlowStatistic(ConnectPoint connectPoint);
-
-    /**
-     * Fetches the current observed flow stats values.
-     *
-     * @param connectPoint the port to fetch information for
-     * @return set of current values
-     */
-    Set<FlowEntry> getPreviousFlowStatistic(ConnectPoint connectPoint);
-}
+/*
+ * 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.net.statistic;
+
+import org.onosproject.net.ConnectPoint;
+import org.onosproject.net.flow.FlowEntry;
+import org.onosproject.net.flow.FlowRule;
+
+import java.util.Set;
+
+/**
+ * Flow Store to house the computed statistics.
+ */
+public interface FlowStatisticStore {
+    /**
+     * Remove entries associated with this rule.
+     *
+     * @param rule {@link org.onosproject.net.flow.FlowRule}
+     */
+    void removeFlowStatistic(FlowRule rule);
+
+    /**
+     * Adds a flow stats observation for a flow rule. The previous flow will be removed.
+     *
+     * @param rule a {@link org.onosproject.net.flow.FlowEntry}
+     */
+    void addFlowStatistic(FlowEntry rule);
+
+    /**
+     * Updates a stats observation for a flow rule. The old flow stats will be moved to previous stats.
+     *
+     * @param rule a {@link org.onosproject.net.flow.FlowEntry}
+     */
+    void updateFlowStatistic(FlowEntry rule);
+
+    /**
+     * Fetches the current observed flow stats values.
+     *
+     * @param connectPoint the port to fetch information for
+     * @return set of current flow rules
+     */
+    Set<FlowEntry> getCurrentFlowStatistic(ConnectPoint connectPoint);
+
+    /**
+     * Fetches the current observed flow stats values.
+     *
+     * @param connectPoint the port to fetch information for
+     * @return set of current values
+     */
+    Set<FlowEntry> getPreviousFlowStatistic(ConnectPoint connectPoint);
+}
diff --git a/core/api/src/main/java/org/onosproject/net/statistic/SummaryFlowEntryWithLoad.java b/core/api/src/main/java/org/onosproject/net/statistic/SummaryFlowEntryWithLoad.java
index 1ec427c..e98774c 100644
--- a/core/api/src/main/java/org/onosproject/net/statistic/SummaryFlowEntryWithLoad.java
+++ b/core/api/src/main/java/org/onosproject/net/statistic/SummaryFlowEntryWithLoad.java
@@ -1,157 +1,157 @@
-/*
- * 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.net.statistic;
-
-import org.onosproject.net.ConnectPoint;
-
-/**
- * Summary Load classified by flow live type.
- */
-public class SummaryFlowEntryWithLoad {
-    private ConnectPoint cp;
-    private Load totalLoad;
-    private Load immediateLoad;
-    private Load shortLoad;
-    private Load midLoad;
-    private Load longLoad;
-    private Load unknownLoad;
-
-    /**
-     * Creates a new summary flow entry having load for the given connect point and total load.
-     *
-     * @param cp        connect point
-     * @param totalLoad total load
-     */
-    public SummaryFlowEntryWithLoad(ConnectPoint cp, Load totalLoad) {
-        this.cp = cp;
-        this.totalLoad = totalLoad;
-        this.immediateLoad = new DefaultLoad();
-        this.shortLoad = new DefaultLoad();
-        this.midLoad = new DefaultLoad();
-        this.longLoad = new DefaultLoad();
-        this.unknownLoad = new DefaultLoad();
-    }
-
-    /**
-     * Creates a new summary flow entry having load for the given connect point
-     * and total, immediate, short, mid, and long load.
-     *
-     * @param cp        connect point
-     * @param totalLoad total load
-     * @param immediateLoad immediate load
-     * @param shortLoad short load
-     * @param midLoad mid load
-     * @param longLoad long load
-     */
-    public SummaryFlowEntryWithLoad(ConnectPoint cp,
-                                    Load totalLoad, Load immediateLoad, Load shortLoad, Load midLoad, Load longLoad) {
-        this.cp = cp;
-        this.totalLoad = totalLoad;
-        this.immediateLoad = immediateLoad;
-        this.shortLoad = shortLoad;
-        this.midLoad = midLoad;
-        this.longLoad = longLoad;
-        this.unknownLoad = new DefaultLoad();
-    }
-
-    /**
-     * Creates a new summary flow entry having load for the given connect point
-     * and total, immediate, short, mid, long, and unknown load.
-     *
-     * @param cp        connect point
-     * @param totalLoad total load
-     * @param immediateLoad immediate load
-     * @param shortLoad short load
-     * @param midLoad mid load
-     * @param longLoad long load
-     * @param unknownLoad long load
-     */
-    public SummaryFlowEntryWithLoad(ConnectPoint cp,
-                                    Load totalLoad, Load immediateLoad,
-                                    Load shortLoad, Load midLoad, Load longLoad, Load unknownLoad) {
-        this.cp = cp;
-        this.totalLoad = totalLoad;
-        this.immediateLoad = immediateLoad;
-        this.shortLoad = shortLoad;
-        this.midLoad = midLoad;
-        this.longLoad = longLoad;
-        this.unknownLoad = unknownLoad;
-    }
-
-    /**
-     * Returns connect point.
-     *
-     * @return connect point
-     */
-    public ConnectPoint connectPoint() {
-        return cp;
-    }
-
-    /**
-     * Returns total load of connect point.
-     *
-     * @return total load
-     */
-    public Load totalLoad() {
-        return totalLoad;
-    }
-
-    /**
-     * Returns immediate load of connect point.
-     *
-     * @return immediate load
-     */
-    public Load immediateLoad() {
-        return immediateLoad;
-    }
-
-    /**
-     * Returns short load of connect point.
-     *
-     * @return short load
-     */
-    public Load shortLoad() {
-        return shortLoad;
-    }
-
-    /**
-     * Returns mid load of connect point.
-     *
-     * @return mid load
-     */
-    public Load midLoad() {
-        return midLoad;
-    }
-
-    /**
-     * Returns long load of connect point.
-     *
-     * @return long load
-     */
-    public Load longLoad() {
-        return longLoad;
-    }
-
-    /**
-     * Returns unknown load of connect point.
-     *
-     * @return unknown load
-     */
-    public Load unknownLoad() {
-        return unknownLoad;
-    }
-}
+/*
+ * 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.net.statistic;
+
+import org.onosproject.net.ConnectPoint;
+
+/**
+ * Summary Load classified by flow live type.
+ */
+public class SummaryFlowEntryWithLoad {
+    private ConnectPoint cp;
+    private Load totalLoad;
+    private Load immediateLoad;
+    private Load shortLoad;
+    private Load midLoad;
+    private Load longLoad;
+    private Load unknownLoad;
+
+    /**
+     * Creates a new summary flow entry having load for the given connect point and total load.
+     *
+     * @param cp        connect point
+     * @param totalLoad total load
+     */
+    public SummaryFlowEntryWithLoad(ConnectPoint cp, Load totalLoad) {
+        this.cp = cp;
+        this.totalLoad = totalLoad;
+        this.immediateLoad = new DefaultLoad();
+        this.shortLoad = new DefaultLoad();
+        this.midLoad = new DefaultLoad();
+        this.longLoad = new DefaultLoad();
+        this.unknownLoad = new DefaultLoad();
+    }
+
+    /**
+     * Creates a new summary flow entry having load for the given connect point
+     * and total, immediate, short, mid, and long load.
+     *
+     * @param cp        connect point
+     * @param totalLoad total load
+     * @param immediateLoad immediate load
+     * @param shortLoad short load
+     * @param midLoad mid load
+     * @param longLoad long load
+     */
+    public SummaryFlowEntryWithLoad(ConnectPoint cp,
+                                    Load totalLoad, Load immediateLoad, Load shortLoad, Load midLoad, Load longLoad) {
+        this.cp = cp;
+        this.totalLoad = totalLoad;
+        this.immediateLoad = immediateLoad;
+        this.shortLoad = shortLoad;
+        this.midLoad = midLoad;
+        this.longLoad = longLoad;
+        this.unknownLoad = new DefaultLoad();
+    }
+
+    /**
+     * Creates a new summary flow entry having load for the given connect point
+     * and total, immediate, short, mid, long, and unknown load.
+     *
+     * @param cp        connect point
+     * @param totalLoad total load
+     * @param immediateLoad immediate load
+     * @param shortLoad short load
+     * @param midLoad mid load
+     * @param longLoad long load
+     * @param unknownLoad long load
+     */
+    public SummaryFlowEntryWithLoad(ConnectPoint cp,
+                                    Load totalLoad, Load immediateLoad,
+                                    Load shortLoad, Load midLoad, Load longLoad, Load unknownLoad) {
+        this.cp = cp;
+        this.totalLoad = totalLoad;
+        this.immediateLoad = immediateLoad;
+        this.shortLoad = shortLoad;
+        this.midLoad = midLoad;
+        this.longLoad = longLoad;
+        this.unknownLoad = unknownLoad;
+    }
+
+    /**
+     * Returns connect point.
+     *
+     * @return connect point
+     */
+    public ConnectPoint connectPoint() {
+        return cp;
+    }
+
+    /**
+     * Returns total load of connect point.
+     *
+     * @return total load
+     */
+    public Load totalLoad() {
+        return totalLoad;
+    }
+
+    /**
+     * Returns immediate load of connect point.
+     *
+     * @return immediate load
+     */
+    public Load immediateLoad() {
+        return immediateLoad;
+    }
+
+    /**
+     * Returns short load of connect point.
+     *
+     * @return short load
+     */
+    public Load shortLoad() {
+        return shortLoad;
+    }
+
+    /**
+     * Returns mid load of connect point.
+     *
+     * @return mid load
+     */
+    public Load midLoad() {
+        return midLoad;
+    }
+
+    /**
+     * Returns long load of connect point.
+     *
+     * @return long load
+     */
+    public Load longLoad() {
+        return longLoad;
+    }
+
+    /**
+     * Returns unknown load of connect point.
+     *
+     * @return unknown load
+     */
+    public Load unknownLoad() {
+        return unknownLoad;
+    }
+}
diff --git a/core/api/src/main/java/org/onosproject/net/statistic/TypedFlowEntryWithLoad.java b/core/api/src/main/java/org/onosproject/net/statistic/TypedFlowEntryWithLoad.java
index a4cbd7d..9d23ade 100644
--- a/core/api/src/main/java/org/onosproject/net/statistic/TypedFlowEntryWithLoad.java
+++ b/core/api/src/main/java/org/onosproject/net/statistic/TypedFlowEntryWithLoad.java
@@ -1,171 +1,171 @@
-/*
- * 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.net.statistic;
-
-import org.onosproject.net.ConnectPoint;
-import org.onosproject.net.flow.FlowEntry;
-import org.onosproject.net.flow.TypedStoredFlowEntry;
-import org.onosproject.net.flow.DefaultTypedFlowEntry;
-
-import static com.google.common.base.Preconditions.checkNotNull;
-
-/**
- * Load of flow entry of flow live type.
- */
-public class TypedFlowEntryWithLoad {
-    private ConnectPoint cp;
-    private TypedStoredFlowEntry tfe;
-    private Load load;
-
-    //TODO: make this variables class, and share with NewAdaptivceFlowStatsCollector class
-    private static final int CAL_AND_POLL_INTERVAL = 5; // means SHORT_POLL_INTERVAL
-    private static final int MID_POLL_INTERVAL = 10;
-    private static final int LONG_POLL_INTERVAL = 15;
-
-    /**
-     * Creates a new typed flow entry with load.
-     *
-     * @param cp connect point
-     * @param tfe typed flow entry
-     * @param load load
-     */
-    public TypedFlowEntryWithLoad(ConnectPoint cp, TypedStoredFlowEntry tfe, Load load) {
-        this.cp = cp;
-        this.tfe = tfe;
-        this.load = load;
-    }
-
-    /**
-     * Creates a new typed flow entry with load.
-     *
-     * @param cp connect point
-     * @param tfe typed flow entry
-     */
-    public TypedFlowEntryWithLoad(ConnectPoint cp, TypedStoredFlowEntry tfe) {
-        this.cp = cp;
-        this.tfe = tfe;
-        this.load = new DefaultLoad(tfe.bytes(), 0, typedPollInterval(tfe));
-    }
-
-    /**
-     * Creates a new typed flow entry with load.
-     *
-     * @param cp connect point
-     * @param fe flow entry
-     */
-    public TypedFlowEntryWithLoad(ConnectPoint cp, FlowEntry fe) {
-        this.cp = cp;
-        this.tfe = newTypedStoredFlowEntry(fe);
-        this.load = new DefaultLoad(fe.bytes(), 0, typedPollInterval(this.tfe));
-    }
-
-    public ConnectPoint connectPoint() {
-        return cp;
-    }
-    public TypedStoredFlowEntry typedStoredFlowEntry() {
-        return tfe;
-    }
-    public Load load() {
-        return load;
-    }
-    public void setLoad(Load load) {
-        this.load = load;
-    }
-
-    /**
-     * Returns short polling interval.
-     *
-     * @return short poll interval
-     */
-    public static int shortPollInterval() {
-        return CAL_AND_POLL_INTERVAL;
-    }
-
-    /**
-     * Returns mid polling interval.
-     *
-     * @return mid poll interval
-     */
-    public static int midPollInterval() {
-        return MID_POLL_INTERVAL;
-    }
-
-    /**
-     * Returns long polling interval.
-     *
-     * @return long poll interval
-     */
-    public static int longPollInterval() {
-        return LONG_POLL_INTERVAL;
-    }
-
-    /**
-     * Returns average polling interval.
-     *
-     * @return average poll interval
-     */
-    public static int avgPollInterval() {
-        return (CAL_AND_POLL_INTERVAL + MID_POLL_INTERVAL + LONG_POLL_INTERVAL) / 3;
-    }
-
-    /**
-     * Returns current typed flow entry's polling interval.
-     *
-     * @param tfe typed flow entry
-     * @return typed poll interval
-     */
-    public static long typedPollInterval(TypedStoredFlowEntry tfe) {
-        checkNotNull(tfe, "TypedStoredFlowEntry cannot be null");
-
-        switch (tfe.flowLiveType()) {
-            case LONG_FLOW:
-                return LONG_POLL_INTERVAL;
-            case MID_FLOW:
-                return MID_POLL_INTERVAL;
-            case SHORT_FLOW:
-            case IMMEDIATE_FLOW:
-            default:
-                return CAL_AND_POLL_INTERVAL;
-        }
-    }
-
-    /**
-     * Creates a new typed flow entry with the given flow entry fe.
-     *
-     * @param fe flow entry
-     * @return new typed flow entry
-     */
-    public static TypedStoredFlowEntry newTypedStoredFlowEntry(FlowEntry fe) {
-        if (fe == null) {
-            return null;
-        }
-
-        long life = fe.life();
-
-        if (life >= LONG_POLL_INTERVAL) {
-            return new DefaultTypedFlowEntry(fe, TypedStoredFlowEntry.FlowLiveType.LONG_FLOW);
-        } else if (life >= MID_POLL_INTERVAL) {
-            return new DefaultTypedFlowEntry(fe, TypedStoredFlowEntry.FlowLiveType.MID_FLOW);
-        } else if (life >= CAL_AND_POLL_INTERVAL) {
-            return new DefaultTypedFlowEntry(fe, TypedStoredFlowEntry.FlowLiveType.SHORT_FLOW);
-        } else if (life >= 0) {
-            return new DefaultTypedFlowEntry(fe, TypedStoredFlowEntry.FlowLiveType.IMMEDIATE_FLOW);
-        } else { // life < 0
-            return new DefaultTypedFlowEntry(fe, TypedStoredFlowEntry.FlowLiveType.UNKNOWN_FLOW);
-        }
-    }
-}
+/*
+ * 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.net.statistic;
+
+import org.onosproject.net.ConnectPoint;
+import org.onosproject.net.flow.FlowEntry;
+import org.onosproject.net.flow.TypedStoredFlowEntry;
+import org.onosproject.net.flow.DefaultTypedFlowEntry;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+
+/**
+ * Load of flow entry of flow live type.
+ */
+public class TypedFlowEntryWithLoad {
+    private ConnectPoint cp;
+    private TypedStoredFlowEntry tfe;
+    private Load load;
+
+    //TODO: make this variables class, and share with NewAdaptivceFlowStatsCollector class
+    private static final int CAL_AND_POLL_INTERVAL = 5; // means SHORT_POLL_INTERVAL
+    private static final int MID_POLL_INTERVAL = 10;
+    private static final int LONG_POLL_INTERVAL = 15;
+
+    /**
+     * Creates a new typed flow entry with load.
+     *
+     * @param cp connect point
+     * @param tfe typed flow entry
+     * @param load load
+     */
+    public TypedFlowEntryWithLoad(ConnectPoint cp, TypedStoredFlowEntry tfe, Load load) {
+        this.cp = cp;
+        this.tfe = tfe;
+        this.load = load;
+    }
+
+    /**
+     * Creates a new typed flow entry with load.
+     *
+     * @param cp connect point
+     * @param tfe typed flow entry
+     */
+    public TypedFlowEntryWithLoad(ConnectPoint cp, TypedStoredFlowEntry tfe) {
+        this.cp = cp;
+        this.tfe = tfe;
+        this.load = new DefaultLoad(tfe.bytes(), 0, typedPollInterval(tfe));
+    }
+
+    /**
+     * Creates a new typed flow entry with load.
+     *
+     * @param cp connect point
+     * @param fe flow entry
+     */
+    public TypedFlowEntryWithLoad(ConnectPoint cp, FlowEntry fe) {
+        this.cp = cp;
+        this.tfe = newTypedStoredFlowEntry(fe);
+        this.load = new DefaultLoad(fe.bytes(), 0, typedPollInterval(this.tfe));
+    }
+
+    public ConnectPoint connectPoint() {
+        return cp;
+    }
+    public TypedStoredFlowEntry typedStoredFlowEntry() {
+        return tfe;
+    }
+    public Load load() {
+        return load;
+    }
+    public void setLoad(Load load) {
+        this.load = load;
+    }
+
+    /**
+     * Returns short polling interval.
+     *
+     * @return short poll interval
+     */
+    public static int shortPollInterval() {
+        return CAL_AND_POLL_INTERVAL;
+    }
+
+    /**
+     * Returns mid polling interval.
+     *
+     * @return mid poll interval
+     */
+    public static int midPollInterval() {
+        return MID_POLL_INTERVAL;
+    }
+
+    /**
+     * Returns long polling interval.
+     *
+     * @return long poll interval
+     */
+    public static int longPollInterval() {
+        return LONG_POLL_INTERVAL;
+    }
+
+    /**
+     * Returns average polling interval.
+     *
+     * @return average poll interval
+     */
+    public static int avgPollInterval() {
+        return (CAL_AND_POLL_INTERVAL + MID_POLL_INTERVAL + LONG_POLL_INTERVAL) / 3;
+    }
+
+    /**
+     * Returns current typed flow entry's polling interval.
+     *
+     * @param tfe typed flow entry
+     * @return typed poll interval
+     */
+    public static long typedPollInterval(TypedStoredFlowEntry tfe) {
+        checkNotNull(tfe, "TypedStoredFlowEntry cannot be null");
+
+        switch (tfe.flowLiveType()) {
+            case LONG_FLOW:
+                return LONG_POLL_INTERVAL;
+            case MID_FLOW:
+                return MID_POLL_INTERVAL;
+            case SHORT_FLOW:
+            case IMMEDIATE_FLOW:
+            default:
+                return CAL_AND_POLL_INTERVAL;
+        }
+    }
+
+    /**
+     * Creates a new typed flow entry with the given flow entry fe.
+     *
+     * @param fe flow entry
+     * @return new typed flow entry
+     */
+    public static TypedStoredFlowEntry newTypedStoredFlowEntry(FlowEntry fe) {
+        if (fe == null) {
+            return null;
+        }
+
+        long life = fe.life();
+
+        if (life >= LONG_POLL_INTERVAL) {
+            return new DefaultTypedFlowEntry(fe, TypedStoredFlowEntry.FlowLiveType.LONG_FLOW);
+        } else if (life >= MID_POLL_INTERVAL) {
+            return new DefaultTypedFlowEntry(fe, TypedStoredFlowEntry.FlowLiveType.MID_FLOW);
+        } else if (life >= CAL_AND_POLL_INTERVAL) {
+            return new DefaultTypedFlowEntry(fe, TypedStoredFlowEntry.FlowLiveType.SHORT_FLOW);
+        } else if (life >= 0) {
+            return new DefaultTypedFlowEntry(fe, TypedStoredFlowEntry.FlowLiveType.IMMEDIATE_FLOW);
+        } else { // life < 0
+            return new DefaultTypedFlowEntry(fe, TypedStoredFlowEntry.FlowLiveType.UNKNOWN_FLOW);
+        }
+    }
+}
diff --git a/core/net/src/main/java/org/onosproject/net/statistic/impl/FlowStatisticManager.java b/core/net/src/main/java/org/onosproject/net/statistic/impl/FlowStatisticManager.java
index f18c56d..75e8c00 100644
--- a/core/net/src/main/java/org/onosproject/net/statistic/impl/FlowStatisticManager.java
+++ b/core/net/src/main/java/org/onosproject/net/statistic/impl/FlowStatisticManager.java
@@ -1,634 +1,634 @@
-/*
- * 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.net.statistic.impl;
-
-import com.google.common.base.MoreObjects;
-import com.google.common.base.Predicate;
-import com.google.common.collect.ImmutableSet;
-import org.apache.felix.scr.annotations.Activate;
-import org.apache.felix.scr.annotations.Component;
-import org.apache.felix.scr.annotations.Deactivate;
-import org.apache.felix.scr.annotations.Reference;
-import org.apache.felix.scr.annotations.ReferenceCardinality;
-import org.apache.felix.scr.annotations.Service;
-import org.onosproject.cli.Comparators;
-import org.onosproject.net.ConnectPoint;
-import org.onosproject.net.Device;
-import org.onosproject.net.Port;
-import org.onosproject.net.PortNumber;
-import org.onosproject.net.device.DeviceService;
-import org.onosproject.net.flow.DefaultTypedFlowEntry;
-import org.onosproject.net.flow.FlowEntry;
-import org.onosproject.net.flow.FlowRule;
-import org.onosproject.net.flow.FlowRuleEvent;
-import org.onosproject.net.flow.FlowRuleListener;
-import org.onosproject.net.flow.FlowRuleService;
-import org.onosproject.net.flow.TypedStoredFlowEntry;
-import org.onosproject.net.flow.instructions.Instruction;
-import org.onosproject.net.statistic.DefaultLoad;
-import org.onosproject.net.statistic.FlowStatisticService;
-import org.onosproject.net.statistic.Load;
-import org.onosproject.net.statistic.FlowStatisticStore;
-import org.onosproject.net.statistic.SummaryFlowEntryWithLoad;
-import org.onosproject.net.statistic.TypedFlowEntryWithLoad;
-
-import org.slf4j.Logger;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.Objects;
-import java.util.Set;
-import java.util.TreeMap;
-import java.util.stream.Collectors;
-
-import static com.google.common.base.Preconditions.checkNotNull;
-import static org.onosproject.security.AppGuard.checkPermission;
-import static org.slf4j.LoggerFactory.getLogger;
-import static org.onosproject.security.AppPermission.Type.*;
-
-/**
- * Provides an implementation of the Flow Statistic Service.
- */
-@Component(immediate = true, enabled = true)
-@Service
-public class FlowStatisticManager implements FlowStatisticService {
-    private final Logger log = getLogger(getClass());
-
-    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
-    protected FlowRuleService flowRuleService;
-
-    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
-    protected FlowStatisticStore flowStatisticStore;
-
-    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
-    protected DeviceService deviceService;
-
-    private final InternalFlowRuleStatsListener frListener = new InternalFlowRuleStatsListener();
-
-    @Activate
-    public void activate() {
-        flowRuleService.addListener(frListener);
-        log.info("Started");
-    }
-
-    @Deactivate
-    public void deactivate() {
-        flowRuleService.removeListener(frListener);
-        log.info("Stopped");
-    }
-
-    @Override
-    public Map<ConnectPoint, SummaryFlowEntryWithLoad> loadSummary(Device device) {
-        checkPermission(STATISTIC_READ);
-
-        Map<ConnectPoint, SummaryFlowEntryWithLoad> summaryLoad = new TreeMap<>(Comparators.CONNECT_POINT_COMPARATOR);
-
-        if (device == null) {
-            return summaryLoad;
-        }
-
-        List<Port> ports = new ArrayList<>(deviceService.getPorts(device.id()));
-
-        for (Port port : ports) {
-            ConnectPoint cp = new ConnectPoint(device.id(), port.number());
-            SummaryFlowEntryWithLoad sfe = loadSummaryPortInternal(cp);
-            summaryLoad.put(cp, sfe);
-        }
-
-        return summaryLoad;
-    }
-
-    @Override
-    public SummaryFlowEntryWithLoad loadSummary(Device device, PortNumber pNumber) {
-        checkPermission(STATISTIC_READ);
-
-        ConnectPoint cp = new ConnectPoint(device.id(), pNumber);
-        return loadSummaryPortInternal(cp);
-    }
-
-    @Override
-    public Map<ConnectPoint, List<TypedFlowEntryWithLoad>> loadAllByType(Device device,
-                                                                  TypedStoredFlowEntry.FlowLiveType liveType,
-                                                                  Instruction.Type instType) {
-        checkPermission(STATISTIC_READ);
-
-        Map<ConnectPoint, List<TypedFlowEntryWithLoad>> allLoad = new TreeMap<>(Comparators.CONNECT_POINT_COMPARATOR);
-
-        if (device == null) {
-            return allLoad;
-        }
-
-        List<Port> ports = new ArrayList<>(deviceService.getPorts(device.id()));
-
-        for (Port port : ports) {
-            ConnectPoint cp = new ConnectPoint(device.id(), port.number());
-            List<TypedFlowEntryWithLoad> tfel = loadAllPortInternal(cp, liveType, instType);
-            allLoad.put(cp, tfel);
-        }
-
-        return allLoad;
-    }
-
-    @Override
-    public List<TypedFlowEntryWithLoad> loadAllByType(Device device, PortNumber pNumber,
-                                               TypedStoredFlowEntry.FlowLiveType liveType,
-                                               Instruction.Type instType) {
-        checkPermission(STATISTIC_READ);
-
-        ConnectPoint cp = new ConnectPoint(device.id(), pNumber);
-        return loadAllPortInternal(cp, liveType, instType);
-    }
-
-    @Override
-    public Map<ConnectPoint, List<TypedFlowEntryWithLoad>> loadTopnByType(Device device,
-                                                                   TypedStoredFlowEntry.FlowLiveType liveType,
-                                                                   Instruction.Type instType,
-                                                                   int topn) {
-        checkPermission(STATISTIC_READ);
-
-        Map<ConnectPoint, List<TypedFlowEntryWithLoad>> allLoad = new TreeMap<>(Comparators.CONNECT_POINT_COMPARATOR);
-
-        if (device == null) {
-            return allLoad;
-        }
-
-        List<Port> ports = new ArrayList<>(deviceService.getPorts(device.id()));
-
-        for (Port port : ports) {
-            ConnectPoint cp = new ConnectPoint(device.id(), port.number());
-            List<TypedFlowEntryWithLoad> tfel = loadTopnPortInternal(cp, liveType, instType, topn);
-            allLoad.put(cp, tfel);
-        }
-
-        return allLoad;
-    }
-
-    @Override
-    public List<TypedFlowEntryWithLoad> loadTopnByType(Device device, PortNumber pNumber,
-                                                TypedStoredFlowEntry.FlowLiveType liveType,
-                                                Instruction.Type instType,
-                                                int topn) {
-        checkPermission(STATISTIC_READ);
-
-        ConnectPoint cp = new ConnectPoint(device.id(), pNumber);
-        return loadTopnPortInternal(cp, liveType, instType, topn);
-    }
-
-    private SummaryFlowEntryWithLoad loadSummaryPortInternal(ConnectPoint cp) {
-        checkPermission(STATISTIC_READ);
-
-        Set<FlowEntry> currentStats;
-        Set<FlowEntry> previousStats;
-
-        TypedStatistics typedStatistics;
-        synchronized (flowStatisticStore) {
-             currentStats = flowStatisticStore.getCurrentFlowStatistic(cp);
-            if (currentStats == null) {
-                return new SummaryFlowEntryWithLoad(cp, new DefaultLoad());
-            }
-            previousStats = flowStatisticStore.getPreviousFlowStatistic(cp);
-            if (previousStats == null) {
-                return new SummaryFlowEntryWithLoad(cp, new DefaultLoad());
-            }
-            // copy to local flow entry
-            typedStatistics = new TypedStatistics(currentStats, previousStats);
-
-            // Check for validity of this stats data
-            checkLoadValidity(currentStats, previousStats);
-        }
-
-        // current and previous set is not empty!
-        Set<FlowEntry> currentSet = typedStatistics.current();
-        Set<FlowEntry> previousSet = typedStatistics.previous();
-        Load totalLoad = new DefaultLoad(aggregateBytesSet(currentSet), aggregateBytesSet(previousSet),
-                TypedFlowEntryWithLoad.avgPollInterval());
-
-        Map<FlowRule, TypedStoredFlowEntry> currentMap;
-        Map<FlowRule, TypedStoredFlowEntry> previousMap;
-
-        currentMap = typedStatistics.currentImmediate();
-        previousMap = typedStatistics.previousImmediate();
-        Load immediateLoad = new DefaultLoad(aggregateBytesMap(currentMap), aggregateBytesMap(previousMap),
-                TypedFlowEntryWithLoad.shortPollInterval());
-
-        currentMap = typedStatistics.currentShort();
-        previousMap = typedStatistics.previousShort();
-        Load shortLoad = new DefaultLoad(aggregateBytesMap(currentMap), aggregateBytesMap(previousMap),
-                TypedFlowEntryWithLoad.shortPollInterval());
-
-        currentMap = typedStatistics.currentMid();
-        previousMap = typedStatistics.previousMid();
-        Load midLoad = new DefaultLoad(aggregateBytesMap(currentMap), aggregateBytesMap(previousMap),
-                TypedFlowEntryWithLoad.midPollInterval());
-
-        currentMap = typedStatistics.currentLong();
-        previousMap = typedStatistics.previousLong();
-        Load longLoad = new DefaultLoad(aggregateBytesMap(currentMap), aggregateBytesMap(previousMap),
-                TypedFlowEntryWithLoad.longPollInterval());
-
-        currentMap = typedStatistics.currentUnknown();
-        previousMap = typedStatistics.previousUnknown();
-        Load unknownLoad = new DefaultLoad(aggregateBytesMap(currentMap), aggregateBytesMap(previousMap),
-                TypedFlowEntryWithLoad.avgPollInterval());
-
-        return new SummaryFlowEntryWithLoad(cp, totalLoad, immediateLoad, shortLoad, midLoad, longLoad, unknownLoad);
-    }
-
-    private List<TypedFlowEntryWithLoad> loadAllPortInternal(ConnectPoint cp,
-                                                             TypedStoredFlowEntry.FlowLiveType liveType,
-                                                             Instruction.Type instType) {
-        checkPermission(STATISTIC_READ);
-
-        List<TypedFlowEntryWithLoad> retTfel = new ArrayList<>();
-
-        Set<FlowEntry> currentStats;
-        Set<FlowEntry> previousStats;
-
-        TypedStatistics typedStatistics;
-        synchronized (flowStatisticStore) {
-            currentStats = flowStatisticStore.getCurrentFlowStatistic(cp);
-            if (currentStats == null) {
-                return retTfel;
-            }
-            previousStats = flowStatisticStore.getPreviousFlowStatistic(cp);
-            if (previousStats == null) {
-                return retTfel;
-            }
-            // copy to local flow entry set
-            typedStatistics = new TypedStatistics(currentStats, previousStats);
-
-            // Check for validity of this stats data
-            checkLoadValidity(currentStats, previousStats);
-        }
-
-        // current and previous set is not empty!
-        boolean isAllLiveType = (liveType == null ? true : false); // null is all live type
-        boolean isAllInstType = (instType == null ? true : false); // null is all inst type
-
-        Map<FlowRule, TypedStoredFlowEntry> currentMap;
-        Map<FlowRule, TypedStoredFlowEntry> previousMap;
-
-        if (isAllLiveType || liveType == TypedStoredFlowEntry.FlowLiveType.IMMEDIATE_FLOW) {
-            currentMap = typedStatistics.currentImmediate();
-            previousMap = typedStatistics.previousImmediate();
-
-            List<TypedFlowEntryWithLoad> fel = typedFlowEntryLoadByInstInternal(cp, currentMap, previousMap,
-                    isAllInstType, instType, TypedFlowEntryWithLoad.shortPollInterval());
-            if (fel.size() > 0) {
-                retTfel.addAll(fel);
-            }
-        }
-
-        if (isAllLiveType || liveType == TypedStoredFlowEntry.FlowLiveType.SHORT_FLOW) {
-            currentMap = typedStatistics.currentShort();
-            previousMap = typedStatistics.previousShort();
-
-            List<TypedFlowEntryWithLoad> fel = typedFlowEntryLoadByInstInternal(cp, currentMap, previousMap,
-                    isAllInstType, instType, TypedFlowEntryWithLoad.shortPollInterval());
-            if (fel.size() > 0) {
-                retTfel.addAll(fel);
-            }
-        }
-
-        if (isAllLiveType || liveType == TypedStoredFlowEntry.FlowLiveType.MID_FLOW) {
-            currentMap = typedStatistics.currentMid();
-            previousMap = typedStatistics.previousMid();
-
-            List<TypedFlowEntryWithLoad> fel = typedFlowEntryLoadByInstInternal(cp, currentMap, previousMap,
-                    isAllInstType, instType, TypedFlowEntryWithLoad.midPollInterval());
-            if (fel.size() > 0) {
-                retTfel.addAll(fel);
-            }
-        }
-
-        if (isAllLiveType || liveType == TypedStoredFlowEntry.FlowLiveType.LONG_FLOW) {
-            currentMap = typedStatistics.currentLong();
-            previousMap = typedStatistics.previousLong();
-
-            List<TypedFlowEntryWithLoad> fel = typedFlowEntryLoadByInstInternal(cp, currentMap, previousMap,
-                    isAllInstType, instType, TypedFlowEntryWithLoad.longPollInterval());
-            if (fel.size() > 0) {
-                retTfel.addAll(fel);
-            }
-        }
-
-        if (isAllLiveType || liveType == TypedStoredFlowEntry.FlowLiveType.UNKNOWN_FLOW) {
-            currentMap = typedStatistics.currentUnknown();
-            previousMap = typedStatistics.previousUnknown();
-
-            List<TypedFlowEntryWithLoad> fel = typedFlowEntryLoadByInstInternal(cp, currentMap, previousMap,
-                    isAllInstType, instType, TypedFlowEntryWithLoad.avgPollInterval());
-            if (fel.size() > 0) {
-                retTfel.addAll(fel);
-            }
-        }
-
-        return retTfel;
-    }
-
-    private List<TypedFlowEntryWithLoad> typedFlowEntryLoadByInstInternal(ConnectPoint cp,
-                                                                      Map<FlowRule, TypedStoredFlowEntry> currentMap,
-                                                                      Map<FlowRule, TypedStoredFlowEntry> previousMap,
-                                                                      boolean isAllInstType,
-                                                                      Instruction.Type instType,
-                                                                      int liveTypePollInterval) {
-        List<TypedFlowEntryWithLoad> fel = new ArrayList<>();
-
-        for (TypedStoredFlowEntry tfe : currentMap.values()) {
-            if (isAllInstType ||
-                    tfe.treatment().allInstructions().stream().
-                            filter(i -> i.type() == instType).
-                            findAny().isPresent()) {
-                long currentBytes = tfe.bytes();
-                long previousBytes = previousMap.getOrDefault(tfe, new DefaultTypedFlowEntry((FlowRule) tfe)).bytes();
-                Load fLoad = new DefaultLoad(currentBytes, previousBytes, liveTypePollInterval);
-                fel.add(new TypedFlowEntryWithLoad(cp, tfe, fLoad));
-            }
-        }
-
-        return fel;
-    }
-
-    private List<TypedFlowEntryWithLoad> loadTopnPortInternal(ConnectPoint cp,
-                                                             TypedStoredFlowEntry.FlowLiveType liveType,
-                                                             Instruction.Type instType,
-                                                             int topn) {
-        List<TypedFlowEntryWithLoad> fel = loadAllPortInternal(cp, liveType, instType);
-
-        // Sort with descending order of load
-        List<TypedFlowEntryWithLoad> tfel =
-                fel.stream().sorted(Comparators.TYPEFLOWENTRY_WITHLOAD_COMPARATOR).
-                        limit(topn).collect(Collectors.toList());
-
-        return tfel;
-    }
-
-    private long aggregateBytesSet(Set<FlowEntry> setFE) {
-        return setFE.stream().mapToLong(FlowEntry::bytes).sum();
-    }
-
-    private long aggregateBytesMap(Map<FlowRule, TypedStoredFlowEntry> mapFE) {
-        return mapFE.values().stream().mapToLong(FlowEntry::bytes).sum();
-    }
-
-    /**
-     * Internal data class holding two set of typed flow entries.
-     */
-    private static class TypedStatistics {
-        private final ImmutableSet<FlowEntry> currentAll;
-        private final ImmutableSet<FlowEntry> previousAll;
-
-        private final Map<FlowRule, TypedStoredFlowEntry> currentImmediate = new HashMap<>();
-        private final Map<FlowRule, TypedStoredFlowEntry> previousImmediate = new HashMap<>();
-
-        private final Map<FlowRule, TypedStoredFlowEntry> currentShort = new HashMap<>();
-        private final Map<FlowRule, TypedStoredFlowEntry> previousShort = new HashMap<>();
-
-        private final Map<FlowRule, TypedStoredFlowEntry> currentMid = new HashMap<>();
-        private final Map<FlowRule, TypedStoredFlowEntry> previousMid = new HashMap<>();
-
-        private final Map<FlowRule, TypedStoredFlowEntry> currentLong = new HashMap<>();
-        private final Map<FlowRule, TypedStoredFlowEntry> previousLong = new HashMap<>();
-
-        private final Map<FlowRule, TypedStoredFlowEntry> currentUnknown = new HashMap<>();
-        private final Map<FlowRule, TypedStoredFlowEntry> previousUnknown = new HashMap<>();
-
-        public TypedStatistics(Set<FlowEntry> current, Set<FlowEntry> previous) {
-            this.currentAll = ImmutableSet.copyOf(checkNotNull(current));
-            this.previousAll = ImmutableSet.copyOf(checkNotNull(previous));
-
-            currentAll.forEach(fe -> {
-                TypedStoredFlowEntry tfe = TypedFlowEntryWithLoad.newTypedStoredFlowEntry(fe);
-
-                switch (tfe.flowLiveType()) {
-                    case IMMEDIATE_FLOW:
-                        currentImmediate.put(fe, tfe);
-                        break;
-                    case SHORT_FLOW:
-                        currentShort.put(fe, tfe);
-                        break;
-                    case MID_FLOW:
-                        currentMid.put(fe, tfe);
-                        break;
-                    case LONG_FLOW:
-                        currentLong.put(fe, tfe);
-                        break;
-                    default:
-                        currentUnknown.put(fe, tfe);
-                        break;
-                }
-            });
-
-            previousAll.forEach(fe -> {
-                TypedStoredFlowEntry tfe = TypedFlowEntryWithLoad.newTypedStoredFlowEntry(fe);
-
-                switch (tfe.flowLiveType()) {
-                    case IMMEDIATE_FLOW:
-                        if (currentImmediate.containsKey(fe)) {
-                            previousImmediate.put(fe, tfe);
-                        } else if (currentShort.containsKey(fe)) {
-                            previousShort.put(fe, tfe);
-                        } else if (currentMid.containsKey(fe)) {
-                            previousMid.put(fe, tfe);
-                        } else if (currentLong.containsKey(fe)) {
-                            previousLong.put(fe, tfe);
-                        } else {
-                            previousUnknown.put(fe, tfe);
-                        }
-                        break;
-                    case SHORT_FLOW:
-                        if (currentShort.containsKey(fe)) {
-                            previousShort.put(fe, tfe);
-                        } else if (currentMid.containsKey(fe)) {
-                            previousMid.put(fe, tfe);
-                        } else if (currentLong.containsKey(fe)) {
-                            previousLong.put(fe, tfe);
-                        } else {
-                            previousUnknown.put(fe, tfe);
-                        }
-                        break;
-                    case MID_FLOW:
-                        if (currentMid.containsKey(fe)) {
-                            previousMid.put(fe, tfe);
-                        } else if (currentLong.containsKey(fe)) {
-                            previousLong.put(fe, tfe);
-                        } else {
-                            previousUnknown.put(fe, tfe);
-                        }
-                        break;
-                    case LONG_FLOW:
-                        if (currentLong.containsKey(fe)) {
-                            previousLong.put(fe, tfe);
-                        } else {
-                            previousUnknown.put(fe, tfe);
-                        }
-                        break;
-                    default:
-                        previousUnknown.put(fe, tfe);
-                        break;
-                }
-            });
-        }
-
-        /**
-         * Returns flow entries as the current value.
-         *
-         * @return flow entries as the current value
-         */
-        public ImmutableSet<FlowEntry> current() {
-            return currentAll;
-        }
-
-        /**
-         * Returns flow entries as the previous value.
-         *
-         * @return flow entries as the previous value
-         */
-        public ImmutableSet<FlowEntry> previous() {
-            return previousAll;
-        }
-
-        public Map<FlowRule, TypedStoredFlowEntry> currentImmediate() {
-            return currentImmediate;
-        }
-        public Map<FlowRule, TypedStoredFlowEntry> previousImmediate() {
-            return previousImmediate;
-        }
-        public Map<FlowRule, TypedStoredFlowEntry> currentShort() {
-            return currentShort;
-        }
-        public Map<FlowRule, TypedStoredFlowEntry> previousShort() {
-            return previousShort;
-        }
-        public Map<FlowRule, TypedStoredFlowEntry> currentMid() {
-            return currentMid;
-        }
-        public Map<FlowRule, TypedStoredFlowEntry> previousMid() {
-            return previousMid;
-        }
-        public Map<FlowRule, TypedStoredFlowEntry> currentLong() {
-            return currentLong;
-        }
-        public Map<FlowRule, TypedStoredFlowEntry> previousLong() {
-            return previousLong;
-        }
-        public Map<FlowRule, TypedStoredFlowEntry> currentUnknown() {
-            return currentUnknown;
-        }
-        public Map<FlowRule, TypedStoredFlowEntry> previousUnknown() {
-            return previousUnknown;
-        }
-
-        /**
-         * Validates values are not empty.
-         *
-         * @return false if either of the sets is empty. Otherwise, true.
-         */
-        public boolean isValid() {
-            return !(currentAll.isEmpty() || previousAll.isEmpty());
-        }
-
-        @Override
-        public int hashCode() {
-            return Objects.hash(currentAll, previousAll);
-        }
-
-        @Override
-        public boolean equals(Object obj) {
-            if (this == obj) {
-                return true;
-            }
-            if (!(obj instanceof TypedStatistics)) {
-                return false;
-            }
-            final TypedStatistics other = (TypedStatistics) obj;
-            return Objects.equals(this.currentAll, other.currentAll) &&
-                    Objects.equals(this.previousAll, other.previousAll);
-        }
-
-        @Override
-        public String toString() {
-            return MoreObjects.toStringHelper(this)
-                    .add("current", currentAll)
-                    .add("previous", previousAll)
-                    .toString();
-        }
-    }
-
-    private void checkLoadValidity(Set<FlowEntry> current, Set<FlowEntry> previous) {
-        current.stream().forEach(c -> {
-            FlowEntry f = previous.stream().filter(p -> c.equals(p)).
-                    findAny().orElse(null);
-            if (f != null && c.bytes() < f.bytes()) {
-                log.debug("FlowStatisticManager:checkLoadValidity():" +
-                        "Error: " + c + " :Previous bytes=" + f.bytes() +
-                        " is larger than current bytes=" + c.bytes() + " !!!");
-            }
-        });
-
-    }
-
-    /**
-     * Creates a predicate that checks the instruction type of a flow entry is the same as
-     * the specified instruction type.
-     *
-     * @param instType instruction type to be checked
-     * @return predicate
-     */
-    private static Predicate<FlowEntry> hasInstructionType(Instruction.Type instType) {
-        return new Predicate<FlowEntry>() {
-            @Override
-            public boolean apply(FlowEntry flowEntry) {
-                List<Instruction> allInstructions = flowEntry.treatment().allInstructions();
-
-                return allInstructions.stream().filter(i -> i.type() == instType).findAny().isPresent();
-            }
-        };
-    }
-
-    /**
-     * Internal flow rule event listener for FlowStatisticManager.
-     */
-    private class InternalFlowRuleStatsListener implements FlowRuleListener {
-
-        @Override
-        public void event(FlowRuleEvent event) {
-            FlowRule rule = event.subject();
-            switch (event.type()) {
-                case RULE_ADDED:
-                    if (rule instanceof FlowEntry) {
-                        flowStatisticStore.addFlowStatistic((FlowEntry) rule);
-                    }
-                    break;
-                case RULE_UPDATED:
-                    flowStatisticStore.updateFlowStatistic((FlowEntry) rule);
-                    break;
-                case RULE_ADD_REQUESTED:
-                    break;
-                case RULE_REMOVE_REQUESTED:
-                    break;
-                case RULE_REMOVED:
-                    flowStatisticStore.removeFlowStatistic(rule);
-                    break;
-                default:
-                    log.warn("Unknown flow rule event {}", event);
-            }
-        }
-    }
-}
+/*
+ * 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.net.statistic.impl;
+
+import com.google.common.base.MoreObjects;
+import com.google.common.base.Predicate;
+import com.google.common.collect.ImmutableSet;
+import org.apache.felix.scr.annotations.Activate;
+import org.apache.felix.scr.annotations.Component;
+import org.apache.felix.scr.annotations.Deactivate;
+import org.apache.felix.scr.annotations.Reference;
+import org.apache.felix.scr.annotations.ReferenceCardinality;
+import org.apache.felix.scr.annotations.Service;
+import org.onosproject.cli.Comparators;
+import org.onosproject.net.ConnectPoint;
+import org.onosproject.net.Device;
+import org.onosproject.net.Port;
+import org.onosproject.net.PortNumber;
+import org.onosproject.net.device.DeviceService;
+import org.onosproject.net.flow.DefaultTypedFlowEntry;
+import org.onosproject.net.flow.FlowEntry;
+import org.onosproject.net.flow.FlowRule;
+import org.onosproject.net.flow.FlowRuleEvent;
+import org.onosproject.net.flow.FlowRuleListener;
+import org.onosproject.net.flow.FlowRuleService;
+import org.onosproject.net.flow.TypedStoredFlowEntry;
+import org.onosproject.net.flow.instructions.Instruction;
+import org.onosproject.net.statistic.DefaultLoad;
+import org.onosproject.net.statistic.FlowStatisticService;
+import org.onosproject.net.statistic.Load;
+import org.onosproject.net.statistic.FlowStatisticStore;
+import org.onosproject.net.statistic.SummaryFlowEntryWithLoad;
+import org.onosproject.net.statistic.TypedFlowEntryWithLoad;
+
+import org.slf4j.Logger;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
+import java.util.Set;
+import java.util.TreeMap;
+import java.util.stream.Collectors;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static org.onosproject.security.AppGuard.checkPermission;
+import static org.slf4j.LoggerFactory.getLogger;
+import static org.onosproject.security.AppPermission.Type.*;
+
+/**
+ * Provides an implementation of the Flow Statistic Service.
+ */
+@Component(immediate = true, enabled = true)
+@Service
+public class FlowStatisticManager implements FlowStatisticService {
+    private final Logger log = getLogger(getClass());
+
+    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
+    protected FlowRuleService flowRuleService;
+
+    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
+    protected FlowStatisticStore flowStatisticStore;
+
+    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
+    protected DeviceService deviceService;
+
+    private final InternalFlowRuleStatsListener frListener = new InternalFlowRuleStatsListener();
+
+    @Activate
+    public void activate() {
+        flowRuleService.addListener(frListener);
+        log.info("Started");
+    }
+
+    @Deactivate
+    public void deactivate() {
+        flowRuleService.removeListener(frListener);
+        log.info("Stopped");
+    }
+
+    @Override
+    public Map<ConnectPoint, SummaryFlowEntryWithLoad> loadSummary(Device device) {
+        checkPermission(STATISTIC_READ);
+
+        Map<ConnectPoint, SummaryFlowEntryWithLoad> summaryLoad = new TreeMap<>(Comparators.CONNECT_POINT_COMPARATOR);
+
+        if (device == null) {
+            return summaryLoad;
+        }
+
+        List<Port> ports = new ArrayList<>(deviceService.getPorts(device.id()));
+
+        for (Port port : ports) {
+            ConnectPoint cp = new ConnectPoint(device.id(), port.number());
+            SummaryFlowEntryWithLoad sfe = loadSummaryPortInternal(cp);
+            summaryLoad.put(cp, sfe);
+        }
+
+        return summaryLoad;
+    }
+
+    @Override
+    public SummaryFlowEntryWithLoad loadSummary(Device device, PortNumber pNumber) {
+        checkPermission(STATISTIC_READ);
+
+        ConnectPoint cp = new ConnectPoint(device.id(), pNumber);
+        return loadSummaryPortInternal(cp);
+    }
+
+    @Override
+    public Map<ConnectPoint, List<TypedFlowEntryWithLoad>> loadAllByType(Device device,
+                                                                  TypedStoredFlowEntry.FlowLiveType liveType,
+                                                                  Instruction.Type instType) {
+        checkPermission(STATISTIC_READ);
+
+        Map<ConnectPoint, List<TypedFlowEntryWithLoad>> allLoad = new TreeMap<>(Comparators.CONNECT_POINT_COMPARATOR);
+
+        if (device == null) {
+            return allLoad;
+        }
+
+        List<Port> ports = new ArrayList<>(deviceService.getPorts(device.id()));
+
+        for (Port port : ports) {
+            ConnectPoint cp = new ConnectPoint(device.id(), port.number());
+            List<TypedFlowEntryWithLoad> tfel = loadAllPortInternal(cp, liveType, instType);
+            allLoad.put(cp, tfel);
+        }
+
+        return allLoad;
+    }
+
+    @Override
+    public List<TypedFlowEntryWithLoad> loadAllByType(Device device, PortNumber pNumber,
+                                               TypedStoredFlowEntry.FlowLiveType liveType,
+                                               Instruction.Type instType) {
+        checkPermission(STATISTIC_READ);
+
+        ConnectPoint cp = new ConnectPoint(device.id(), pNumber);
+        return loadAllPortInternal(cp, liveType, instType);
+    }
+
+    @Override
+    public Map<ConnectPoint, List<TypedFlowEntryWithLoad>> loadTopnByType(Device device,
+                                                                   TypedStoredFlowEntry.FlowLiveType liveType,
+                                                                   Instruction.Type instType,
+                                                                   int topn) {
+        checkPermission(STATISTIC_READ);
+
+        Map<ConnectPoint, List<TypedFlowEntryWithLoad>> allLoad = new TreeMap<>(Comparators.CONNECT_POINT_COMPARATOR);
+
+        if (device == null) {
+            return allLoad;
+        }
+
+        List<Port> ports = new ArrayList<>(deviceService.getPorts(device.id()));
+
+        for (Port port : ports) {
+            ConnectPoint cp = new ConnectPoint(device.id(), port.number());
+            List<TypedFlowEntryWithLoad> tfel = loadTopnPortInternal(cp, liveType, instType, topn);
+            allLoad.put(cp, tfel);
+        }
+
+        return allLoad;
+    }
+
+    @Override
+    public List<TypedFlowEntryWithLoad> loadTopnByType(Device device, PortNumber pNumber,
+                                                TypedStoredFlowEntry.FlowLiveType liveType,
+                                                Instruction.Type instType,
+                                                int topn) {
+        checkPermission(STATISTIC_READ);
+
+        ConnectPoint cp = new ConnectPoint(device.id(), pNumber);
+        return loadTopnPortInternal(cp, liveType, instType, topn);
+    }
+
+    private SummaryFlowEntryWithLoad loadSummaryPortInternal(ConnectPoint cp) {
+        checkPermission(STATISTIC_READ);
+
+        Set<FlowEntry> currentStats;
+        Set<FlowEntry> previousStats;
+
+        TypedStatistics typedStatistics;
+        synchronized (flowStatisticStore) {
+             currentStats = flowStatisticStore.getCurrentFlowStatistic(cp);
+            if (currentStats == null) {
+                return new SummaryFlowEntryWithLoad(cp, new DefaultLoad());
+            }
+            previousStats = flowStatisticStore.getPreviousFlowStatistic(cp);
+            if (previousStats == null) {
+                return new SummaryFlowEntryWithLoad(cp, new DefaultLoad());
+            }
+            // copy to local flow entry
+            typedStatistics = new TypedStatistics(currentStats, previousStats);
+
+            // Check for validity of this stats data
+            checkLoadValidity(currentStats, previousStats);
+        }
+
+        // current and previous set is not empty!
+        Set<FlowEntry> currentSet = typedStatistics.current();
+        Set<FlowEntry> previousSet = typedStatistics.previous();
+        Load totalLoad = new DefaultLoad(aggregateBytesSet(currentSet), aggregateBytesSet(previousSet),
+                TypedFlowEntryWithLoad.avgPollInterval());
+
+        Map<FlowRule, TypedStoredFlowEntry> currentMap;
+        Map<FlowRule, TypedStoredFlowEntry> previousMap;
+
+        currentMap = typedStatistics.currentImmediate();
+        previousMap = typedStatistics.previousImmediate();
+        Load immediateLoad = new DefaultLoad(aggregateBytesMap(currentMap), aggregateBytesMap(previousMap),
+                TypedFlowEntryWithLoad.shortPollInterval());
+
+        currentMap = typedStatistics.currentShort();
+        previousMap = typedStatistics.previousShort();
+        Load shortLoad = new DefaultLoad(aggregateBytesMap(currentMap), aggregateBytesMap(previousMap),
+                TypedFlowEntryWithLoad.shortPollInterval());
+
+        currentMap = typedStatistics.currentMid();
+        previousMap = typedStatistics.previousMid();
+        Load midLoad = new DefaultLoad(aggregateBytesMap(currentMap), aggregateBytesMap(previousMap),
+                TypedFlowEntryWithLoad.midPollInterval());
+
+        currentMap = typedStatistics.currentLong();
+        previousMap = typedStatistics.previousLong();
+        Load longLoad = new DefaultLoad(aggregateBytesMap(currentMap), aggregateBytesMap(previousMap),
+                TypedFlowEntryWithLoad.longPollInterval());
+
+        currentMap = typedStatistics.currentUnknown();
+        previousMap = typedStatistics.previousUnknown();
+        Load unknownLoad = new DefaultLoad(aggregateBytesMap(currentMap), aggregateBytesMap(previousMap),
+                TypedFlowEntryWithLoad.avgPollInterval());
+
+        return new SummaryFlowEntryWithLoad(cp, totalLoad, immediateLoad, shortLoad, midLoad, longLoad, unknownLoad);
+    }
+
+    private List<TypedFlowEntryWithLoad> loadAllPortInternal(ConnectPoint cp,
+                                                             TypedStoredFlowEntry.FlowLiveType liveType,
+                                                             Instruction.Type instType) {
+        checkPermission(STATISTIC_READ);
+
+        List<TypedFlowEntryWithLoad> retTfel = new ArrayList<>();
+
+        Set<FlowEntry> currentStats;
+        Set<FlowEntry> previousStats;
+
+        TypedStatistics typedStatistics;
+        synchronized (flowStatisticStore) {
+            currentStats = flowStatisticStore.getCurrentFlowStatistic(cp);
+            if (currentStats == null) {
+                return retTfel;
+            }
+            previousStats = flowStatisticStore.getPreviousFlowStatistic(cp);
+            if (previousStats == null) {
+                return retTfel;
+            }
+            // copy to local flow entry set
+            typedStatistics = new TypedStatistics(currentStats, previousStats);
+
+            // Check for validity of this stats data
+            checkLoadValidity(currentStats, previousStats);
+        }
+
+        // current and previous set is not empty!
+        boolean isAllLiveType = (liveType == null ? true : false); // null is all live type
+        boolean isAllInstType = (instType == null ? true : false); // null is all inst type
+
+        Map<FlowRule, TypedStoredFlowEntry> currentMap;
+        Map<FlowRule, TypedStoredFlowEntry> previousMap;
+
+        if (isAllLiveType || liveType == TypedStoredFlowEntry.FlowLiveType.IMMEDIATE_FLOW) {
+            currentMap = typedStatistics.currentImmediate();
+            previousMap = typedStatistics.previousImmediate();
+
+            List<TypedFlowEntryWithLoad> fel = typedFlowEntryLoadByInstInternal(cp, currentMap, previousMap,
+                    isAllInstType, instType, TypedFlowEntryWithLoad.shortPollInterval());
+            if (fel.size() > 0) {
+                retTfel.addAll(fel);
+            }
+        }
+
+        if (isAllLiveType || liveType == TypedStoredFlowEntry.FlowLiveType.SHORT_FLOW) {
+            currentMap = typedStatistics.currentShort();
+            previousMap = typedStatistics.previousShort();
+
+            List<TypedFlowEntryWithLoad> fel = typedFlowEntryLoadByInstInternal(cp, currentMap, previousMap,
+                    isAllInstType, instType, TypedFlowEntryWithLoad.shortPollInterval());
+            if (fel.size() > 0) {
+                retTfel.addAll(fel);
+            }
+        }
+
+        if (isAllLiveType || liveType == TypedStoredFlowEntry.FlowLiveType.MID_FLOW) {
+            currentMap = typedStatistics.currentMid();
+            previousMap = typedStatistics.previousMid();
+
+            List<TypedFlowEntryWithLoad> fel = typedFlowEntryLoadByInstInternal(cp, currentMap, previousMap,
+                    isAllInstType, instType, TypedFlowEntryWithLoad.midPollInterval());
+            if (fel.size() > 0) {
+                retTfel.addAll(fel);
+            }
+        }
+
+        if (isAllLiveType || liveType == TypedStoredFlowEntry.FlowLiveType.LONG_FLOW) {
+            currentMap = typedStatistics.currentLong();
+            previousMap = typedStatistics.previousLong();
+
+            List<TypedFlowEntryWithLoad> fel = typedFlowEntryLoadByInstInternal(cp, currentMap, previousMap,
+                    isAllInstType, instType, TypedFlowEntryWithLoad.longPollInterval());
+            if (fel.size() > 0) {
+                retTfel.addAll(fel);
+            }
+        }
+
+        if (isAllLiveType || liveType == TypedStoredFlowEntry.FlowLiveType.UNKNOWN_FLOW) {
+            currentMap = typedStatistics.currentUnknown();
+            previousMap = typedStatistics.previousUnknown();
+
+            List<TypedFlowEntryWithLoad> fel = typedFlowEntryLoadByInstInternal(cp, currentMap, previousMap,
+                    isAllInstType, instType, TypedFlowEntryWithLoad.avgPollInterval());
+            if (fel.size() > 0) {
+                retTfel.addAll(fel);
+            }
+        }
+
+        return retTfel;
+    }
+
+    private List<TypedFlowEntryWithLoad> typedFlowEntryLoadByInstInternal(ConnectPoint cp,
+                                                                      Map<FlowRule, TypedStoredFlowEntry> currentMap,
+                                                                      Map<FlowRule, TypedStoredFlowEntry> previousMap,
+                                                                      boolean isAllInstType,
+                                                                      Instruction.Type instType,
+                                                                      int liveTypePollInterval) {
+        List<TypedFlowEntryWithLoad> fel = new ArrayList<>();
+
+        for (TypedStoredFlowEntry tfe : currentMap.values()) {
+            if (isAllInstType ||
+                    tfe.treatment().allInstructions().stream().
+                            filter(i -> i.type() == instType).
+                            findAny().isPresent()) {
+                long currentBytes = tfe.bytes();
+                long previousBytes = previousMap.getOrDefault(tfe, new DefaultTypedFlowEntry((FlowRule) tfe)).bytes();
+                Load fLoad = new DefaultLoad(currentBytes, previousBytes, liveTypePollInterval);
+                fel.add(new TypedFlowEntryWithLoad(cp, tfe, fLoad));
+            }
+        }
+
+        return fel;
+    }
+
+    private List<TypedFlowEntryWithLoad> loadTopnPortInternal(ConnectPoint cp,
+                                                             TypedStoredFlowEntry.FlowLiveType liveType,
+                                                             Instruction.Type instType,
+                                                             int topn) {
+        List<TypedFlowEntryWithLoad> fel = loadAllPortInternal(cp, liveType, instType);
+
+        // Sort with descending order of load
+        List<TypedFlowEntryWithLoad> tfel =
+                fel.stream().sorted(Comparators.TYPEFLOWENTRY_WITHLOAD_COMPARATOR).
+                        limit(topn).collect(Collectors.toList());
+
+        return tfel;
+    }
+
+    private long aggregateBytesSet(Set<FlowEntry> setFE) {
+        return setFE.stream().mapToLong(FlowEntry::bytes).sum();
+    }
+
+    private long aggregateBytesMap(Map<FlowRule, TypedStoredFlowEntry> mapFE) {
+        return mapFE.values().stream().mapToLong(FlowEntry::bytes).sum();
+    }
+
+    /**
+     * Internal data class holding two set of typed flow entries.
+     */
+    private static class TypedStatistics {
+        private final ImmutableSet<FlowEntry> currentAll;
+        private final ImmutableSet<FlowEntry> previousAll;
+
+        private final Map<FlowRule, TypedStoredFlowEntry> currentImmediate = new HashMap<>();
+        private final Map<FlowRule, TypedStoredFlowEntry> previousImmediate = new HashMap<>();
+
+        private final Map<FlowRule, TypedStoredFlowEntry> currentShort = new HashMap<>();
+        private final Map<FlowRule, TypedStoredFlowEntry> previousShort = new HashMap<>();
+
+        private final Map<FlowRule, TypedStoredFlowEntry> currentMid = new HashMap<>();
+        private final Map<FlowRule, TypedStoredFlowEntry> previousMid = new HashMap<>();
+
+        private final Map<FlowRule, TypedStoredFlowEntry> currentLong = new HashMap<>();
+        private final Map<FlowRule, TypedStoredFlowEntry> previousLong = new HashMap<>();
+
+        private final Map<FlowRule, TypedStoredFlowEntry> currentUnknown = new HashMap<>();
+        private final Map<FlowRule, TypedStoredFlowEntry> previousUnknown = new HashMap<>();
+
+        public TypedStatistics(Set<FlowEntry> current, Set<FlowEntry> previous) {
+            this.currentAll = ImmutableSet.copyOf(checkNotNull(current));
+            this.previousAll = ImmutableSet.copyOf(checkNotNull(previous));
+
+            currentAll.forEach(fe -> {
+                TypedStoredFlowEntry tfe = TypedFlowEntryWithLoad.newTypedStoredFlowEntry(fe);
+
+                switch (tfe.flowLiveType()) {
+                    case IMMEDIATE_FLOW:
+                        currentImmediate.put(fe, tfe);
+                        break;
+                    case SHORT_FLOW:
+                        currentShort.put(fe, tfe);
+                        break;
+                    case MID_FLOW:
+                        currentMid.put(fe, tfe);
+                        break;
+                    case LONG_FLOW:
+                        currentLong.put(fe, tfe);
+                        break;
+                    default:
+                        currentUnknown.put(fe, tfe);
+                        break;
+                }
+            });
+
+            previousAll.forEach(fe -> {
+                TypedStoredFlowEntry tfe = TypedFlowEntryWithLoad.newTypedStoredFlowEntry(fe);
+
+                switch (tfe.flowLiveType()) {
+                    case IMMEDIATE_FLOW:
+                        if (currentImmediate.containsKey(fe)) {
+                            previousImmediate.put(fe, tfe);
+                        } else if (currentShort.containsKey(fe)) {
+                            previousShort.put(fe, tfe);
+                        } else if (currentMid.containsKey(fe)) {
+                            previousMid.put(fe, tfe);
+                        } else if (currentLong.containsKey(fe)) {
+                            previousLong.put(fe, tfe);
+                        } else {
+                            previousUnknown.put(fe, tfe);
+                        }
+                        break;
+                    case SHORT_FLOW:
+                        if (currentShort.containsKey(fe)) {
+                            previousShort.put(fe, tfe);
+                        } else if (currentMid.containsKey(fe)) {
+                            previousMid.put(fe, tfe);
+                        } else if (currentLong.containsKey(fe)) {
+                            previousLong.put(fe, tfe);
+                        } else {
+                            previousUnknown.put(fe, tfe);
+                        }
+                        break;
+                    case MID_FLOW:
+                        if (currentMid.containsKey(fe)) {
+                            previousMid.put(fe, tfe);
+                        } else if (currentLong.containsKey(fe)) {
+                            previousLong.put(fe, tfe);
+                        } else {
+                            previousUnknown.put(fe, tfe);
+                        }
+                        break;
+                    case LONG_FLOW:
+                        if (currentLong.containsKey(fe)) {
+                            previousLong.put(fe, tfe);
+                        } else {
+                            previousUnknown.put(fe, tfe);
+                        }
+                        break;
+                    default:
+                        previousUnknown.put(fe, tfe);
+                        break;
+                }
+            });
+        }
+
+        /**
+         * Returns flow entries as the current value.
+         *
+         * @return flow entries as the current value
+         */
+        public ImmutableSet<FlowEntry> current() {
+            return currentAll;
+        }
+
+        /**
+         * Returns flow entries as the previous value.
+         *
+         * @return flow entries as the previous value
+         */
+        public ImmutableSet<FlowEntry> previous() {
+            return previousAll;
+        }
+
+        public Map<FlowRule, TypedStoredFlowEntry> currentImmediate() {
+            return currentImmediate;
+        }
+        public Map<FlowRule, TypedStoredFlowEntry> previousImmediate() {
+            return previousImmediate;
+        }
+        public Map<FlowRule, TypedStoredFlowEntry> currentShort() {
+            return currentShort;
+        }
+        public Map<FlowRule, TypedStoredFlowEntry> previousShort() {
+            return previousShort;
+        }
+        public Map<FlowRule, TypedStoredFlowEntry> currentMid() {
+            return currentMid;
+        }
+        public Map<FlowRule, TypedStoredFlowEntry> previousMid() {
+            return previousMid;
+        }
+        public Map<FlowRule, TypedStoredFlowEntry> currentLong() {
+            return currentLong;
+        }
+        public Map<FlowRule, TypedStoredFlowEntry> previousLong() {
+            return previousLong;
+        }
+        public Map<FlowRule, TypedStoredFlowEntry> currentUnknown() {
+            return currentUnknown;
+        }
+        public Map<FlowRule, TypedStoredFlowEntry> previousUnknown() {
+            return previousUnknown;
+        }
+
+        /**
+         * Validates values are not empty.
+         *
+         * @return false if either of the sets is empty. Otherwise, true.
+         */
+        public boolean isValid() {
+            return !(currentAll.isEmpty() || previousAll.isEmpty());
+        }
+
+        @Override
+        public int hashCode() {
+            return Objects.hash(currentAll, previousAll);
+        }
+
+        @Override
+        public boolean equals(Object obj) {
+            if (this == obj) {
+                return true;
+            }
+            if (!(obj instanceof TypedStatistics)) {
+                return false;
+            }
+            final TypedStatistics other = (TypedStatistics) obj;
+            return Objects.equals(this.currentAll, other.currentAll) &&
+                    Objects.equals(this.previousAll, other.previousAll);
+        }
+
+        @Override
+        public String toString() {
+            return MoreObjects.toStringHelper(this)
+                    .add("current", currentAll)
+                    .add("previous", previousAll)
+                    .toString();
+        }
+    }
+
+    private void checkLoadValidity(Set<FlowEntry> current, Set<FlowEntry> previous) {
+        current.stream().forEach(c -> {
+            FlowEntry f = previous.stream().filter(p -> c.equals(p)).
+                    findAny().orElse(null);
+            if (f != null && c.bytes() < f.bytes()) {
+                log.debug("FlowStatisticManager:checkLoadValidity():" +
+                        "Error: " + c + " :Previous bytes=" + f.bytes() +
+                        " is larger than current bytes=" + c.bytes() + " !!!");
+            }
+        });
+
+    }
+
+    /**
+     * Creates a predicate that checks the instruction type of a flow entry is the same as
+     * the specified instruction type.
+     *
+     * @param instType instruction type to be checked
+     * @return predicate
+     */
+    private static Predicate<FlowEntry> hasInstructionType(Instruction.Type instType) {
+        return new Predicate<FlowEntry>() {
+            @Override
+            public boolean apply(FlowEntry flowEntry) {
+                List<Instruction> allInstructions = flowEntry.treatment().allInstructions();
+
+                return allInstructions.stream().filter(i -> i.type() == instType).findAny().isPresent();
+            }
+        };
+    }
+
+    /**
+     * Internal flow rule event listener for FlowStatisticManager.
+     */
+    private class InternalFlowRuleStatsListener implements FlowRuleListener {
+
+        @Override
+        public void event(FlowRuleEvent event) {
+            FlowRule rule = event.subject();
+            switch (event.type()) {
+                case RULE_ADDED:
+                    if (rule instanceof FlowEntry) {
+                        flowStatisticStore.addFlowStatistic((FlowEntry) rule);
+                    }
+                    break;
+                case RULE_UPDATED:
+                    flowStatisticStore.updateFlowStatistic((FlowEntry) rule);
+                    break;
+                case RULE_ADD_REQUESTED:
+                    break;
+                case RULE_REMOVE_REQUESTED:
+                    break;
+                case RULE_REMOVED:
+                    flowStatisticStore.removeFlowStatistic(rule);
+                    break;
+                default:
+                    log.warn("Unknown flow rule event {}", event);
+            }
+        }
+    }
+}
diff --git a/core/store/dist/src/main/java/org/onosproject/store/statistic/impl/DistributedFlowStatisticStore.java b/core/store/dist/src/main/java/org/onosproject/store/statistic/impl/DistributedFlowStatisticStore.java
index 0cd4a83..cc14eba 100644
--- a/core/store/dist/src/main/java/org/onosproject/store/statistic/impl/DistributedFlowStatisticStore.java
+++ b/core/store/dist/src/main/java/org/onosproject/store/statistic/impl/DistributedFlowStatisticStore.java
@@ -1,289 +1,289 @@
-/*
- * 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.store.statistic.impl;
-
-import com.google.common.base.Objects;
-import org.apache.felix.scr.annotations.Activate;
-import org.apache.felix.scr.annotations.Component;
-import org.apache.felix.scr.annotations.Deactivate;
-import org.apache.felix.scr.annotations.Reference;
-import org.apache.felix.scr.annotations.ReferenceCardinality;
-import org.apache.felix.scr.annotations.Service;
-import org.onlab.util.KryoNamespace;
-import org.onlab.util.Tools;
-import org.onosproject.cluster.ClusterService;
-import org.onosproject.cluster.NodeId;
-import org.onosproject.mastership.MastershipService;
-import org.onosproject.net.ConnectPoint;
-import org.onosproject.net.DeviceId;
-import org.onosproject.net.PortNumber;
-import org.onosproject.net.flow.FlowEntry;
-import org.onosproject.net.flow.FlowRule;
-import org.onosproject.net.flow.instructions.Instruction;
-import org.onosproject.net.flow.instructions.Instructions;
-import org.onosproject.net.statistic.FlowStatisticStore;
-import org.onosproject.store.cluster.messaging.ClusterCommunicationService;
-import org.onosproject.store.serializers.KryoNamespaces;
-import org.onosproject.store.serializers.KryoSerializer;
-import org.slf4j.Logger;
-
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.Map;
-import java.util.Optional;
-import java.util.Set;
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.Executors;
-import java.util.concurrent.TimeUnit;
-
-import static org.onlab.util.Tools.groupedThreads;
-import static org.onosproject.store.statistic.impl.StatisticStoreMessageSubjects.GET_CURRENT;
-import static org.onosproject.store.statistic.impl.StatisticStoreMessageSubjects.GET_PREVIOUS;
-import static org.slf4j.LoggerFactory.getLogger;
-
-/**
- * Maintains flow statistics using RPC calls to collect stats from remote instances
- * on demand.
- */
-@Component(immediate = true)
-@Service
-public class DistributedFlowStatisticStore implements FlowStatisticStore {
-    private final Logger log = getLogger(getClass());
-
-    // TODO: Make configurable.
-    private static final int MESSAGE_HANDLER_THREAD_POOL_SIZE = 4;
-
-    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
-    protected MastershipService mastershipService;
-
-    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
-    protected ClusterCommunicationService clusterCommunicator;
-
-    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
-    protected ClusterService clusterService;
-
-    private Map<ConnectPoint, Set<FlowEntry>> previous =
-            new ConcurrentHashMap<>();
-
-    private Map<ConnectPoint, Set<FlowEntry>> current =
-            new ConcurrentHashMap<>();
-
-    protected static final KryoSerializer SERIALIZER = new KryoSerializer() {
-        @Override
-        protected void setupKryoPool() {
-            serializerPool = KryoNamespace.newBuilder()
-                    .register(KryoNamespaces.API)
-                    .nextId(KryoNamespaces.BEGIN_USER_CUSTOM_ID)
-                            // register this store specific classes here
-                    .build();
-        }
-    };
-
-    private NodeId local;
-    private ExecutorService messageHandlingExecutor;
-
-    private static final long STATISTIC_STORE_TIMEOUT_MILLIS = 3000;
-
-    @Activate
-    public void activate() {
-        local = clusterService.getLocalNode().id();
-
-        messageHandlingExecutor = Executors.newFixedThreadPool(
-                MESSAGE_HANDLER_THREAD_POOL_SIZE,
-                groupedThreads("onos/store/statistic", "message-handlers"));
-
-        clusterCommunicator.addSubscriber(
-                GET_CURRENT, SERIALIZER::decode, this::getCurrentStatisticInternal, SERIALIZER::encode,
-                messageHandlingExecutor);
-
-        clusterCommunicator.addSubscriber(
-                GET_CURRENT, SERIALIZER::decode, this::getPreviousStatisticInternal, SERIALIZER::encode,
-                messageHandlingExecutor);
-
-        log.info("Started");
-    }
-
-    @Deactivate
-    public void deactivate() {
-        clusterCommunicator.removeSubscriber(GET_PREVIOUS);
-        clusterCommunicator.removeSubscriber(GET_CURRENT);
-        messageHandlingExecutor.shutdown();
-        log.info("Stopped");
-    }
-
-    @Override
-    public synchronized void removeFlowStatistic(FlowRule rule) {
-        ConnectPoint cp = buildConnectPoint(rule);
-        if (cp == null) {
-            return;
-        }
-
-        // remove this rule if present from current map
-        current.computeIfPresent(cp, (c, e) -> { e.remove(rule); return e;  });
-
-        // remove this on if present from previous map
-        previous.computeIfPresent(cp, (c, e) -> { e.remove(rule); return e; });
-    }
-
-    @Override
-    public synchronized void addFlowStatistic(FlowEntry rule) {
-        ConnectPoint cp = buildConnectPoint(rule);
-        if (cp == null) {
-            return;
-        }
-
-        // create one if absent and add this rule
-        current.putIfAbsent(cp, new HashSet<>());
-        current.computeIfPresent(cp, (c, e) -> { e.add(rule); return e; });
-
-        // remove previous one if present
-        previous.computeIfPresent(cp, (c, e) -> { e.remove(rule); return e; });
-    }
-
-    public synchronized void updateFlowStatistic(FlowEntry rule) {
-        ConnectPoint cp = buildConnectPoint(rule);
-        if (cp == null) {
-            return;
-        }
-
-        Set<FlowEntry> curr = current.get(cp);
-        if (curr == null) {
-            addFlowStatistic(rule);
-        } else {
-            Optional<FlowEntry> f = curr.stream().filter(c -> rule.equals(c)).
-                    findAny();
-            if (f.isPresent() && rule.bytes() < f.get().bytes()) {
-                log.debug("DistributedFlowStatisticStore:updateFlowStatistic():" +
-                        " Invalid Flow Update! Will be removed!!" +
-                        " curr flowId=" + Long.toHexString(rule.id().value()) +
-                        ", prev flowId=" + Long.toHexString(f.get().id().value()) +
-                        ", curr bytes=" + rule.bytes() + ", prev bytes=" + f.get().bytes() +
-                        ", curr life=" + rule.life() + ", prev life=" + f.get().life() +
-                        ", curr lastSeen=" + rule.lastSeen() + ", prev lastSeen=" + f.get().lastSeen());
-                // something is wrong! invalid flow entry, so delete it
-                removeFlowStatistic(rule);
-                return;
-            }
-            Set<FlowEntry> prev = previous.get(cp);
-            if (prev == null) {
-                prev = new HashSet<>();
-                previous.put(cp, prev);
-            }
-
-            // previous one is exist
-            if (f.isPresent()) {
-                // remove old one and add new one
-                prev.remove(rule);
-                if (!prev.add(f.get())) {
-                    log.debug("DistributedFlowStatisticStore:updateFlowStatistic():" +
-                                    " flowId={}, add failed into previous.",
-                            Long.toHexString(rule.id().value()));
-                }
-            }
-
-            // remove old one and add new one
-            curr.remove(rule);
-            if (!curr.add(rule)) {
-                log.debug("DistributedFlowStatisticStore:updateFlowStatistic():" +
-                                " flowId={}, add failed into current.",
-                        Long.toHexString(rule.id().value()));
-            }
-        }
-    }
-
-    @Override
-    public Set<FlowEntry> getCurrentFlowStatistic(ConnectPoint connectPoint) {
-        final DeviceId deviceId = connectPoint.deviceId();
-
-        NodeId master = mastershipService.getMasterFor(deviceId);
-        if (master == null) {
-            log.warn("No master for {}", deviceId);
-            return Collections.emptySet();
-        }
-
-        if (Objects.equal(local, master)) {
-            return getCurrentStatisticInternal(connectPoint);
-        } else {
-            return Tools.futureGetOrElse(clusterCommunicator.sendAndReceive(
-                            connectPoint,
-                            GET_CURRENT,
-                            SERIALIZER::encode,
-                            SERIALIZER::decode,
-                            master),
-                    STATISTIC_STORE_TIMEOUT_MILLIS,
-                    TimeUnit.MILLISECONDS,
-                    Collections.emptySet());
-        }
-    }
-
-    private synchronized Set<FlowEntry> getCurrentStatisticInternal(ConnectPoint connectPoint) {
-        return current.get(connectPoint);
-    }
-
-    @Override
-    public Set<FlowEntry> getPreviousFlowStatistic(ConnectPoint connectPoint) {
-        final DeviceId deviceId = connectPoint.deviceId();
-
-        NodeId master = mastershipService.getMasterFor(deviceId);
-        if (master == null) {
-            log.warn("No master for {}", deviceId);
-            return Collections.emptySet();
-        }
-
-        if (Objects.equal(local, master)) {
-            return getPreviousStatisticInternal(connectPoint);
-        } else {
-            return Tools.futureGetOrElse(clusterCommunicator.sendAndReceive(
-                            connectPoint,
-                            GET_PREVIOUS,
-                            SERIALIZER::encode,
-                            SERIALIZER::decode,
-                            master),
-                    STATISTIC_STORE_TIMEOUT_MILLIS,
-                    TimeUnit.MILLISECONDS,
-                    Collections.emptySet());
-        }
-    }
-
-    private synchronized Set<FlowEntry> getPreviousStatisticInternal(ConnectPoint connectPoint) {
-        return previous.get(connectPoint);
-    }
-
-    private ConnectPoint buildConnectPoint(FlowRule rule) {
-        PortNumber port = getOutput(rule);
-
-        if (port == null) {
-            return null;
-        }
-        ConnectPoint cp = new ConnectPoint(rule.deviceId(), port);
-        return cp;
-    }
-
-    private PortNumber getOutput(FlowRule rule) {
-        for (Instruction i : rule.treatment().allInstructions()) {
-            if (i.type() == Instruction.Type.OUTPUT) {
-                Instructions.OutputInstruction out = (Instructions.OutputInstruction) i;
-                return out.port();
-            }
-            if (i.type() == Instruction.Type.DROP) {
-                return PortNumber.P0;
-            }
-        }
-        return null;
-    }
+/*
+ * 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.store.statistic.impl;
+
+import com.google.common.base.Objects;
+import org.apache.felix.scr.annotations.Activate;
+import org.apache.felix.scr.annotations.Component;
+import org.apache.felix.scr.annotations.Deactivate;
+import org.apache.felix.scr.annotations.Reference;
+import org.apache.felix.scr.annotations.ReferenceCardinality;
+import org.apache.felix.scr.annotations.Service;
+import org.onlab.util.KryoNamespace;
+import org.onlab.util.Tools;
+import org.onosproject.cluster.ClusterService;
+import org.onosproject.cluster.NodeId;
+import org.onosproject.mastership.MastershipService;
+import org.onosproject.net.ConnectPoint;
+import org.onosproject.net.DeviceId;
+import org.onosproject.net.PortNumber;
+import org.onosproject.net.flow.FlowEntry;
+import org.onosproject.net.flow.FlowRule;
+import org.onosproject.net.flow.instructions.Instruction;
+import org.onosproject.net.flow.instructions.Instructions;
+import org.onosproject.net.statistic.FlowStatisticStore;
+import org.onosproject.store.cluster.messaging.ClusterCommunicationService;
+import org.onosproject.store.serializers.KryoNamespaces;
+import org.onosproject.store.serializers.KryoSerializer;
+import org.slf4j.Logger;
+
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Optional;
+import java.util.Set;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.TimeUnit;
+
+import static org.onlab.util.Tools.groupedThreads;
+import static org.onosproject.store.statistic.impl.StatisticStoreMessageSubjects.GET_CURRENT;
+import static org.onosproject.store.statistic.impl.StatisticStoreMessageSubjects.GET_PREVIOUS;
+import static org.slf4j.LoggerFactory.getLogger;
+
+/**
+ * Maintains flow statistics using RPC calls to collect stats from remote instances
+ * on demand.
+ */
+@Component(immediate = true)
+@Service
+public class DistributedFlowStatisticStore implements FlowStatisticStore {
+    private final Logger log = getLogger(getClass());
+
+    // TODO: Make configurable.
+    private static final int MESSAGE_HANDLER_THREAD_POOL_SIZE = 4;
+
+    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
+    protected MastershipService mastershipService;
+
+    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
+    protected ClusterCommunicationService clusterCommunicator;
+
+    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
+    protected ClusterService clusterService;
+
+    private Map<ConnectPoint, Set<FlowEntry>> previous =
+            new ConcurrentHashMap<>();
+
+    private Map<ConnectPoint, Set<FlowEntry>> current =
+            new ConcurrentHashMap<>();
+
+    protected static final KryoSerializer SERIALIZER = new KryoSerializer() {
+        @Override
+        protected void setupKryoPool() {
+            serializerPool = KryoNamespace.newBuilder()
+                    .register(KryoNamespaces.API)
+                    .nextId(KryoNamespaces.BEGIN_USER_CUSTOM_ID)
+                            // register this store specific classes here
+                    .build();
+        }
+    };
+
+    private NodeId local;
+    private ExecutorService messageHandlingExecutor;
+
+    private static final long STATISTIC_STORE_TIMEOUT_MILLIS = 3000;
+
+    @Activate
+    public void activate() {
+        local = clusterService.getLocalNode().id();
+
+        messageHandlingExecutor = Executors.newFixedThreadPool(
+                MESSAGE_HANDLER_THREAD_POOL_SIZE,
+                groupedThreads("onos/store/statistic", "message-handlers"));
+
+        clusterCommunicator.addSubscriber(
+                GET_CURRENT, SERIALIZER::decode, this::getCurrentStatisticInternal, SERIALIZER::encode,
+                messageHandlingExecutor);
+
+        clusterCommunicator.addSubscriber(
+                GET_CURRENT, SERIALIZER::decode, this::getPreviousStatisticInternal, SERIALIZER::encode,
+                messageHandlingExecutor);
+
+        log.info("Started");
+    }
+
+    @Deactivate
+    public void deactivate() {
+        clusterCommunicator.removeSubscriber(GET_PREVIOUS);
+        clusterCommunicator.removeSubscriber(GET_CURRENT);
+        messageHandlingExecutor.shutdown();
+        log.info("Stopped");
+    }
+
+    @Override
+    public synchronized void removeFlowStatistic(FlowRule rule) {
+        ConnectPoint cp = buildConnectPoint(rule);
+        if (cp == null) {
+            return;
+        }
+
+        // remove this rule if present from current map
+        current.computeIfPresent(cp, (c, e) -> { e.remove(rule); return e;  });
+
+        // remove this on if present from previous map
+        previous.computeIfPresent(cp, (c, e) -> { e.remove(rule); return e; });
+    }
+
+    @Override
+    public synchronized void addFlowStatistic(FlowEntry rule) {
+        ConnectPoint cp = buildConnectPoint(rule);
+        if (cp == null) {
+            return;
+        }
+
+        // create one if absent and add this rule
+        current.putIfAbsent(cp, new HashSet<>());
+        current.computeIfPresent(cp, (c, e) -> { e.add(rule); return e; });
+
+        // remove previous one if present
+        previous.computeIfPresent(cp, (c, e) -> { e.remove(rule); return e; });
+    }
+
+    public synchronized void updateFlowStatistic(FlowEntry rule) {
+        ConnectPoint cp = buildConnectPoint(rule);
+        if (cp == null) {
+            return;
+        }
+
+        Set<FlowEntry> curr = current.get(cp);
+        if (curr == null) {
+            addFlowStatistic(rule);
+        } else {
+            Optional<FlowEntry> f = curr.stream().filter(c -> rule.equals(c)).
+                    findAny();
+            if (f.isPresent() && rule.bytes() < f.get().bytes()) {
+                log.debug("DistributedFlowStatisticStore:updateFlowStatistic():" +
+                        " Invalid Flow Update! Will be removed!!" +
+                        " curr flowId=" + Long.toHexString(rule.id().value()) +
+                        ", prev flowId=" + Long.toHexString(f.get().id().value()) +
+                        ", curr bytes=" + rule.bytes() + ", prev bytes=" + f.get().bytes() +
+                        ", curr life=" + rule.life() + ", prev life=" + f.get().life() +
+                        ", curr lastSeen=" + rule.lastSeen() + ", prev lastSeen=" + f.get().lastSeen());
+                // something is wrong! invalid flow entry, so delete it
+                removeFlowStatistic(rule);
+                return;
+            }
+            Set<FlowEntry> prev = previous.get(cp);
+            if (prev == null) {
+                prev = new HashSet<>();
+                previous.put(cp, prev);
+            }
+
+            // previous one is exist
+            if (f.isPresent()) {
+                // remove old one and add new one
+                prev.remove(rule);
+                if (!prev.add(f.get())) {
+                    log.debug("DistributedFlowStatisticStore:updateFlowStatistic():" +
+                                    " flowId={}, add failed into previous.",
+                            Long.toHexString(rule.id().value()));
+                }
+            }
+
+            // remove old one and add new one
+            curr.remove(rule);
+            if (!curr.add(rule)) {
+                log.debug("DistributedFlowStatisticStore:updateFlowStatistic():" +
+                                " flowId={}, add failed into current.",
+                        Long.toHexString(rule.id().value()));
+            }
+        }
+    }
+
+    @Override
+    public Set<FlowEntry> getCurrentFlowStatistic(ConnectPoint connectPoint) {
+        final DeviceId deviceId = connectPoint.deviceId();
+
+        NodeId master = mastershipService.getMasterFor(deviceId);
+        if (master == null) {
+            log.warn("No master for {}", deviceId);
+            return Collections.emptySet();
+        }
+
+        if (Objects.equal(local, master)) {
+            return getCurrentStatisticInternal(connectPoint);
+        } else {
+            return Tools.futureGetOrElse(clusterCommunicator.sendAndReceive(
+                            connectPoint,
+                            GET_CURRENT,
+                            SERIALIZER::encode,
+                            SERIALIZER::decode,
+                            master),
+                    STATISTIC_STORE_TIMEOUT_MILLIS,
+                    TimeUnit.MILLISECONDS,
+                    Collections.emptySet());
+        }
+    }
+
+    private synchronized Set<FlowEntry> getCurrentStatisticInternal(ConnectPoint connectPoint) {
+        return current.get(connectPoint);
+    }
+
+    @Override
+    public Set<FlowEntry> getPreviousFlowStatistic(ConnectPoint connectPoint) {
+        final DeviceId deviceId = connectPoint.deviceId();
+
+        NodeId master = mastershipService.getMasterFor(deviceId);
+        if (master == null) {
+            log.warn("No master for {}", deviceId);
+            return Collections.emptySet();
+        }
+
+        if (Objects.equal(local, master)) {
+            return getPreviousStatisticInternal(connectPoint);
+        } else {
+            return Tools.futureGetOrElse(clusterCommunicator.sendAndReceive(
+                            connectPoint,
+                            GET_PREVIOUS,
+                            SERIALIZER::encode,
+                            SERIALIZER::decode,
+                            master),
+                    STATISTIC_STORE_TIMEOUT_MILLIS,
+                    TimeUnit.MILLISECONDS,
+                    Collections.emptySet());
+        }
+    }
+
+    private synchronized Set<FlowEntry> getPreviousStatisticInternal(ConnectPoint connectPoint) {
+        return previous.get(connectPoint);
+    }
+
+    private ConnectPoint buildConnectPoint(FlowRule rule) {
+        PortNumber port = getOutput(rule);
+
+        if (port == null) {
+            return null;
+        }
+        ConnectPoint cp = new ConnectPoint(rule.deviceId(), port);
+        return cp;
+    }
+
+    private PortNumber getOutput(FlowRule rule) {
+        for (Instruction i : rule.treatment().allInstructions()) {
+            if (i.type() == Instruction.Type.OUTPUT) {
+                Instructions.OutputInstruction out = (Instructions.OutputInstruction) i;
+                return out.port();
+            }
+            if (i.type() == Instruction.Type.DROP) {
+                return PortNumber.P0;
+            }
+        }
+        return null;
+    }
 }
\ No newline at end of file
diff --git a/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/protocol/BgpFactories.java b/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/protocol/BgpFactories.java
index eb18c7d..32f5c48 100755
--- a/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/protocol/BgpFactories.java
+++ b/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/protocol/BgpFactories.java
@@ -1,82 +1,82 @@
-/*
- * 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.bgpio.protocol;
-
-import org.jboss.netty.buffer.ChannelBuffer;
-import org.onosproject.bgpio.exceptions.BgpParseException;
-import org.onosproject.bgpio.protocol.ver4.BgpFactoryVer4;
-import org.onosproject.bgpio.types.BgpHeader;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-/**
- * Abstraction to provide the version for BGP.
- */
-public final class BgpFactories {
-
-    protected static final Logger log = LoggerFactory.getLogger(BgpFactories.class);
-
-    private static final GenericReader GENERIC_READER = new GenericReader();
-
-    private BgpFactories() {
-    }
-
-    /**
-     * Returns the instance of BGP Version.
-     *
-     * @param version BGP version
-     * @return BGP version
-     */
-    public static BgpFactory getFactory(BgpVersion version) {
-        switch (version) {
-        case BGP_4:
-            return BgpFactoryVer4.INSTANCE;
-        default:
-            throw new IllegalArgumentException("[BgpFactory:]Unknown version: " + version);
-        }
-    }
-
-    /**
-     * Reader class for reading BGP messages from channel buffer.
-     *
-     */
-    private static class GenericReader implements BgpMessageReader<BgpMessage> {
-
-        @Override
-        public BgpMessage readFrom(ChannelBuffer bb, BgpHeader bgpHeader)
-                throws BgpParseException {
-            BgpFactory factory;
-
-            if (!bb.readable()) {
-                log.error("Empty message received");
-                throw new BgpParseException("Empty message received");
-            }
-            // TODO: Currently only BGP version 4 is supported
-            factory = org.onosproject.bgpio.protocol.ver4.BgpFactoryVer4.INSTANCE;
-            return factory.getReader().readFrom(bb, bgpHeader);
-        }
-    }
-
-    /**
-     * Returns BGP messsage generic reader.
-     *
-     * @return bgp message generic reader
-     */
-    public static BgpMessageReader<BgpMessage> getGenericReader() {
-        return GENERIC_READER;
-    }
-}
+/*
+ * 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.bgpio.protocol;
+
+import org.jboss.netty.buffer.ChannelBuffer;
+import org.onosproject.bgpio.exceptions.BgpParseException;
+import org.onosproject.bgpio.protocol.ver4.BgpFactoryVer4;
+import org.onosproject.bgpio.types.BgpHeader;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * Abstraction to provide the version for BGP.
+ */
+public final class BgpFactories {
+
+    protected static final Logger log = LoggerFactory.getLogger(BgpFactories.class);
+
+    private static final GenericReader GENERIC_READER = new GenericReader();
+
+    private BgpFactories() {
+    }
+
+    /**
+     * Returns the instance of BGP Version.
+     *
+     * @param version BGP version
+     * @return BGP version
+     */
+    public static BgpFactory getFactory(BgpVersion version) {
+        switch (version) {
+        case BGP_4:
+            return BgpFactoryVer4.INSTANCE;
+        default:
+            throw new IllegalArgumentException("[BgpFactory:]Unknown version: " + version);
+        }
+    }
+
+    /**
+     * Reader class for reading BGP messages from channel buffer.
+     *
+     */
+    private static class GenericReader implements BgpMessageReader<BgpMessage> {
+
+        @Override
+        public BgpMessage readFrom(ChannelBuffer bb, BgpHeader bgpHeader)
+                throws BgpParseException {
+            BgpFactory factory;
+
+            if (!bb.readable()) {
+                log.error("Empty message received");
+                throw new BgpParseException("Empty message received");
+            }
+            // TODO: Currently only BGP version 4 is supported
+            factory = org.onosproject.bgpio.protocol.ver4.BgpFactoryVer4.INSTANCE;
+            return factory.getReader().readFrom(bb, bgpHeader);
+        }
+    }
+
+    /**
+     * Returns BGP messsage generic reader.
+     *
+     * @return bgp message generic reader
+     */
+    public static BgpMessageReader<BgpMessage> getGenericReader() {
+        return GENERIC_READER;
+    }
+}
diff --git a/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/protocol/linkstate/BgpLinkLsNlriVer4.java b/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/protocol/linkstate/BgpLinkLsNlriVer4.java
index 01d369e..9845b52 100755
--- a/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/protocol/linkstate/BgpLinkLsNlriVer4.java
+++ b/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/protocol/linkstate/BgpLinkLsNlriVer4.java
@@ -1,210 +1,210 @@
-/*
- * 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.bgpio.protocol.linkstate;
-
-import java.util.List;
-
-import org.jboss.netty.buffer.ChannelBuffer;
-import org.onosproject.bgpio.exceptions.BgpParseException;
-import org.onosproject.bgpio.protocol.BgpLinkLsNlri;
-import org.onosproject.bgpio.protocol.NlriType;
-import org.onosproject.bgpio.protocol.linkstate.BgpNodeLSNlriVer4.ProtocolType;
-import org.onosproject.bgpio.types.BgpErrorType;
-import org.onosproject.bgpio.types.BgpValueType;
-import org.onosproject.bgpio.types.RouteDistinguisher;
-import org.onosproject.bgpio.util.Constants;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import com.google.common.base.MoreObjects;
-
-/**
- * Implementation of Link LS NLRI.
- */
-public class BgpLinkLsNlriVer4 implements BgpLinkLsNlri {
-
-    /*
-     * REFERENCE : draft-ietf-idr-ls-distribution-11
-          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
-         +-+-+-+-+-+-+-+-+
-         |  Protocol-ID  |
-         +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-         |                           Identifier                          |
-         |                            (64 bits)                          |
-         +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-         //               Local Node Descriptors (variable)             //
-         +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-         //               Remote Node Descriptors (variable)            //
-         +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-         //                  Link Descriptors (variable)                //
-         +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-
-                          Figure : The Link NLRI format
-     */
-    private static final Logger log = LoggerFactory.getLogger(BgpLinkLsNlriVer4.class);
-    public static final int LINK_NLRITYPE = 2;
-
-    private BgpLinkLSIdentifier linkLSIdentifier;
-    private byte protocolId;
-    private long identifier;
-    private RouteDistinguisher routeDistinguisher;
-    private boolean isVpn;
-
-    /**
-     * Initialize fields.
-     */
-    public BgpLinkLsNlriVer4() {
-        this.protocolId = 0;
-        this.identifier = 0;
-        this.linkLSIdentifier = null;
-        this.routeDistinguisher = null;
-        this.isVpn = false;
-    }
-
-    /**
-     * Constructor to initialize parameters for BGP LinkLSNlri.
-     *
-     * @param protocolId protocol Id
-     * @param identifier field in BGP LinkLSNlri
-     * @param linkLSIdentifier link LS identifier
-     * @param routeDistinguisher route distinguisher from message
-     * @param isVpn vpn info availability in message
-     */
-    public BgpLinkLsNlriVer4(byte protocolId, long identifier, BgpLinkLSIdentifier linkLSIdentifier,
-                             RouteDistinguisher routeDistinguisher, boolean isVpn) {
-        this.protocolId = protocolId;
-        this.identifier = identifier;
-        this.linkLSIdentifier = linkLSIdentifier;
-        this.routeDistinguisher = routeDistinguisher;
-        this.isVpn = isVpn;
-    }
-
-    /**
-     * Reads from channelBuffer and parses Link LS Nlri.
-     *
-     * @param cb ChannelBuffer
-     * @param afi Address Family Identifier
-     * @param safi Subsequent Address Family Identifier
-     * @return object of this class
-     * @throws BgpParseException while parsing Link LS NLRI
-     */
-    public static BgpLinkLsNlriVer4 read(ChannelBuffer cb, short afi, byte safi) throws BgpParseException {
-        boolean isVpn = false;
-        RouteDistinguisher routeDistinguisher = null;
-        if ((afi == Constants.AFI_VALUE) && (safi == Constants.VPN_SAFI_VALUE)) {
-            routeDistinguisher = new RouteDistinguisher();
-            routeDistinguisher = RouteDistinguisher.read(cb);
-            isVpn = true;
-        } else {
-            isVpn = false;
-        }
-        byte protocolId = cb.readByte();
-        long identifier = cb.readLong();
-
-        BgpLinkLSIdentifier linkLSIdentifier = new BgpLinkLSIdentifier();
-        linkLSIdentifier = BgpLinkLSIdentifier.parseLinkIdendifier(cb, protocolId);
-        return new BgpLinkLsNlriVer4(protocolId, identifier, linkLSIdentifier, routeDistinguisher, isVpn);
-    }
-
-    @Override
-    public NlriType getNlriType() {
-        return NlriType.LINK;
-    }
-
-    @Override
-    public long getIdentifier() {
-        return this.identifier;
-    }
-
-    /**
-     * Set the link LS identifier.
-     *
-     * @param linkLSIdentifier link LS identifier to set
-     */
-    public void setLinkLSIdentifier(BgpLinkLSIdentifier linkLSIdentifier) {
-        this.linkLSIdentifier = linkLSIdentifier;
-    }
-
-    @Override
-    public ProtocolType getProtocolId() throws BgpParseException {
-        switch (protocolId) {
-        case Constants.ISIS_LEVELONE:
-            return ProtocolType.ISIS_LEVEL_ONE;
-        case Constants.ISIS_LEVELTWO:
-            return ProtocolType.ISIS_LEVEL_TWO;
-        case Constants.OSPFV2:
-            return ProtocolType.OSPF_V2;
-        case Constants.DIRECT:
-            return ProtocolType.DIRECT;
-        case Constants.STATIC_CONFIGURATION:
-            return ProtocolType.STATIC_CONFIGURATION;
-        case Constants.OSPFV3:
-            return ProtocolType.OSPF_V3;
-        default:
-            throw new BgpParseException(BgpErrorType.UPDATE_MESSAGE_ERROR, (byte) 0, null);
-        }
-    }
-
-    @Override
-    public NodeDescriptors localNodeDescriptors() {
-        return this.linkLSIdentifier.localNodeDescriptors();
-    }
-
-    @Override
-    public NodeDescriptors remoteNodeDescriptors() {
-        return this.linkLSIdentifier.remoteNodeDescriptors();
-    }
-
-    /**
-     * Returns whether VPN is present or not.
-     *
-     * @return whether VPN is present or not
-     */
-    public boolean isVpnPresent() {
-        return this.isVpn;
-    }
-
-    @Override
-    public RouteDistinguisher getRouteDistinguisher() {
-        return this.routeDistinguisher;
-    }
-
-    /**
-     * Returns link identifier.
-     *
-     * @return link identifier
-     */
-    public BgpLinkLSIdentifier getLinkIdentifier() {
-        return this.linkLSIdentifier;
-    }
-
-    @Override
-    public List<BgpValueType> linkDescriptors() {
-        return this.linkLSIdentifier.linkDescriptors();
-    }
-
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(getClass())
-                .omitNullValues()
-                .add("protocolId", protocolId)
-                .add("identifier", identifier)
-                .add("RouteDistinguisher ", routeDistinguisher)
-                .add("linkLSIdentifier", linkLSIdentifier)
-                .toString();
-    }
-}
+/*
+ * 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.bgpio.protocol.linkstate;
+
+import java.util.List;
+
+import org.jboss.netty.buffer.ChannelBuffer;
+import org.onosproject.bgpio.exceptions.BgpParseException;
+import org.onosproject.bgpio.protocol.BgpLinkLsNlri;
+import org.onosproject.bgpio.protocol.NlriType;
+import org.onosproject.bgpio.protocol.linkstate.BgpNodeLSNlriVer4.ProtocolType;
+import org.onosproject.bgpio.types.BgpErrorType;
+import org.onosproject.bgpio.types.BgpValueType;
+import org.onosproject.bgpio.types.RouteDistinguisher;
+import org.onosproject.bgpio.util.Constants;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.google.common.base.MoreObjects;
+
+/**
+ * Implementation of Link LS NLRI.
+ */
+public class BgpLinkLsNlriVer4 implements BgpLinkLsNlri {
+
+    /*
+     * REFERENCE : draft-ietf-idr-ls-distribution-11
+          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
+         +-+-+-+-+-+-+-+-+
+         |  Protocol-ID  |
+         +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+         |                           Identifier                          |
+         |                            (64 bits)                          |
+         +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+         //               Local Node Descriptors (variable)             //
+         +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+         //               Remote Node Descriptors (variable)            //
+         +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+         //                  Link Descriptors (variable)                //
+         +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+
+                          Figure : The Link NLRI format
+     */
+    private static final Logger log = LoggerFactory.getLogger(BgpLinkLsNlriVer4.class);
+    public static final int LINK_NLRITYPE = 2;
+
+    private BgpLinkLSIdentifier linkLSIdentifier;
+    private byte protocolId;
+    private long identifier;
+    private RouteDistinguisher routeDistinguisher;
+    private boolean isVpn;
+
+    /**
+     * Initialize fields.
+     */
+    public BgpLinkLsNlriVer4() {
+        this.protocolId = 0;
+        this.identifier = 0;
+        this.linkLSIdentifier = null;
+        this.routeDistinguisher = null;
+        this.isVpn = false;
+    }
+
+    /**
+     * Constructor to initialize parameters for BGP LinkLSNlri.
+     *
+     * @param protocolId protocol Id
+     * @param identifier field in BGP LinkLSNlri
+     * @param linkLSIdentifier link LS identifier
+     * @param routeDistinguisher route distinguisher from message
+     * @param isVpn vpn info availability in message
+     */
+    public BgpLinkLsNlriVer4(byte protocolId, long identifier, BgpLinkLSIdentifier linkLSIdentifier,
+                             RouteDistinguisher routeDistinguisher, boolean isVpn) {
+        this.protocolId = protocolId;
+        this.identifier = identifier;
+        this.linkLSIdentifier = linkLSIdentifier;
+        this.routeDistinguisher = routeDistinguisher;
+        this.isVpn = isVpn;
+    }
+
+    /**
+     * Reads from channelBuffer and parses Link LS Nlri.
+     *
+     * @param cb ChannelBuffer
+     * @param afi Address Family Identifier
+     * @param safi Subsequent Address Family Identifier
+     * @return object of this class
+     * @throws BgpParseException while parsing Link LS NLRI
+     */
+    public static BgpLinkLsNlriVer4 read(ChannelBuffer cb, short afi, byte safi) throws BgpParseException {
+        boolean isVpn = false;
+        RouteDistinguisher routeDistinguisher = null;
+        if ((afi == Constants.AFI_VALUE) && (safi == Constants.VPN_SAFI_VALUE)) {
+            routeDistinguisher = new RouteDistinguisher();
+            routeDistinguisher = RouteDistinguisher.read(cb);
+            isVpn = true;
+        } else {
+            isVpn = false;
+        }
+        byte protocolId = cb.readByte();
+        long identifier = cb.readLong();
+
+        BgpLinkLSIdentifier linkLSIdentifier = new BgpLinkLSIdentifier();
+        linkLSIdentifier = BgpLinkLSIdentifier.parseLinkIdendifier(cb, protocolId);
+        return new BgpLinkLsNlriVer4(protocolId, identifier, linkLSIdentifier, routeDistinguisher, isVpn);
+    }
+
+    @Override
+    public NlriType getNlriType() {
+        return NlriType.LINK;
+    }
+
+    @Override
+    public long getIdentifier() {
+        return this.identifier;
+    }
+
+    /**
+     * Set the link LS identifier.
+     *
+     * @param linkLSIdentifier link LS identifier to set
+     */
+    public void setLinkLSIdentifier(BgpLinkLSIdentifier linkLSIdentifier) {
+        this.linkLSIdentifier = linkLSIdentifier;
+    }
+
+    @Override
+    public ProtocolType getProtocolId() throws BgpParseException {
+        switch (protocolId) {
+        case Constants.ISIS_LEVELONE:
+            return ProtocolType.ISIS_LEVEL_ONE;
+        case Constants.ISIS_LEVELTWO:
+            return ProtocolType.ISIS_LEVEL_TWO;
+        case Constants.OSPFV2:
+            return ProtocolType.OSPF_V2;
+        case Constants.DIRECT:
+            return ProtocolType.DIRECT;
+        case Constants.STATIC_CONFIGURATION:
+            return ProtocolType.STATIC_CONFIGURATION;
+        case Constants.OSPFV3:
+            return ProtocolType.OSPF_V3;
+        default:
+            throw new BgpParseException(BgpErrorType.UPDATE_MESSAGE_ERROR, (byte) 0, null);
+        }
+    }
+
+    @Override
+    public NodeDescriptors localNodeDescriptors() {
+        return this.linkLSIdentifier.localNodeDescriptors();
+    }
+
+    @Override
+    public NodeDescriptors remoteNodeDescriptors() {
+        return this.linkLSIdentifier.remoteNodeDescriptors();
+    }
+
+    /**
+     * Returns whether VPN is present or not.
+     *
+     * @return whether VPN is present or not
+     */
+    public boolean isVpnPresent() {
+        return this.isVpn;
+    }
+
+    @Override
+    public RouteDistinguisher getRouteDistinguisher() {
+        return this.routeDistinguisher;
+    }
+
+    /**
+     * Returns link identifier.
+     *
+     * @return link identifier
+     */
+    public BgpLinkLSIdentifier getLinkIdentifier() {
+        return this.linkLSIdentifier;
+    }
+
+    @Override
+    public List<BgpValueType> linkDescriptors() {
+        return this.linkLSIdentifier.linkDescriptors();
+    }
+
+    @Override
+    public String toString() {
+        return MoreObjects.toStringHelper(getClass())
+                .omitNullValues()
+                .add("protocolId", protocolId)
+                .add("identifier", identifier)
+                .add("RouteDistinguisher ", routeDistinguisher)
+                .add("linkLSIdentifier", linkLSIdentifier)
+                .toString();
+    }
+}
diff --git a/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/types/FourOctetAsNumCapabilityTlv.java b/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/types/FourOctetAsNumCapabilityTlv.java
index 59db331..5c9275b 100644
--- a/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/types/FourOctetAsNumCapabilityTlv.java
+++ b/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/types/FourOctetAsNumCapabilityTlv.java
@@ -1,120 +1,120 @@
-/*
- * 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.bgpio.types;
-
-import java.util.Objects;
-
-import org.jboss.netty.buffer.ChannelBuffer;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import com.google.common.base.MoreObjects;
-
-/**
- * Provides FourOctetAsNumCapabilityTlv Capability Tlv.
- */
-public class FourOctetAsNumCapabilityTlv implements BgpValueType {
-
-    /**
-     * support to indicate its support for four-octet AS numbers -CAPABILITY TLV format.
-     */
-    protected static final Logger log = LoggerFactory
-            .getLogger(FourOctetAsNumCapabilityTlv.class);
-
-    public static final byte TYPE = 65;
-    public static final byte LENGTH = 4;
-
-    private final int rawValue;
-
-    /**
-     * constructor to initialize rawValue.
-     * @param rawValue FourOctetAsNumCapabilityTlv
-     */
-    public FourOctetAsNumCapabilityTlv(int rawValue) {
-        this.rawValue = rawValue;
-    }
-
-    /**
-     * constructor to initialize raw.
-     * @param raw AS number
-     * @return object of FourOctetAsNumCapabilityTlv
-     */
-    public static FourOctetAsNumCapabilityTlv of(final int raw) {
-        return new FourOctetAsNumCapabilityTlv(raw);
-    }
-
-    /**
-     * Returns value of TLV.
-     * @return int value of rawValue
-     */
-    public int getInt() {
-        return rawValue;
-    }
-
-    @Override
-    public short getType() {
-        return TYPE;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(rawValue);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-        if (obj instanceof FourOctetAsNumCapabilityTlv) {
-            FourOctetAsNumCapabilityTlv other = (FourOctetAsNumCapabilityTlv) obj;
-            return Objects.equals(rawValue, other.rawValue);
-        }
-        return false;
-    }
-
-    @Override
-    public int write(ChannelBuffer cb) {
-        int iLenStartIndex = cb.writerIndex();
-        cb.writeByte(TYPE);
-        cb.writeByte(LENGTH);
-        cb.writeInt(rawValue);
-        return cb.writerIndex() - iLenStartIndex;
-    }
-
-    /**
-     * Reads the channel buffer and returns object of FourOctetAsNumCapabilityTlv.
-     * @param cb type of channel buffer
-     * @return object of FourOctetAsNumCapabilityTlv
-     */
-    public static FourOctetAsNumCapabilityTlv read(ChannelBuffer cb) {
-        return FourOctetAsNumCapabilityTlv.of(cb.readInt());
-    }
-
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(getClass())
-                .add("Type", TYPE)
-                .add("Length", LENGTH)
-                .add("Value", rawValue).toString();
-    }
-
-    @Override
-    public int compareTo(Object o) {
-        // TODO Auto-generated method stub
-        return 0;
-    }
-}
+/*
+ * 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.bgpio.types;
+
+import java.util.Objects;
+
+import org.jboss.netty.buffer.ChannelBuffer;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.google.common.base.MoreObjects;
+
+/**
+ * Provides FourOctetAsNumCapabilityTlv Capability Tlv.
+ */
+public class FourOctetAsNumCapabilityTlv implements BgpValueType {
+
+    /**
+     * support to indicate its support for four-octet AS numbers -CAPABILITY TLV format.
+     */
+    protected static final Logger log = LoggerFactory
+            .getLogger(FourOctetAsNumCapabilityTlv.class);
+
+    public static final byte TYPE = 65;
+    public static final byte LENGTH = 4;
+
+    private final int rawValue;
+
+    /**
+     * constructor to initialize rawValue.
+     * @param rawValue FourOctetAsNumCapabilityTlv
+     */
+    public FourOctetAsNumCapabilityTlv(int rawValue) {
+        this.rawValue = rawValue;
+    }
+
+    /**
+     * constructor to initialize raw.
+     * @param raw AS number
+     * @return object of FourOctetAsNumCapabilityTlv
+     */
+    public static FourOctetAsNumCapabilityTlv of(final int raw) {
+        return new FourOctetAsNumCapabilityTlv(raw);
+    }
+
+    /**
+     * Returns value of TLV.
+     * @return int value of rawValue
+     */
+    public int getInt() {
+        return rawValue;
+    }
+
+    @Override
+    public short getType() {
+        return TYPE;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(rawValue);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+        if (obj instanceof FourOctetAsNumCapabilityTlv) {
+            FourOctetAsNumCapabilityTlv other = (FourOctetAsNumCapabilityTlv) obj;
+            return Objects.equals(rawValue, other.rawValue);
+        }
+        return false;
+    }
+
+    @Override
+    public int write(ChannelBuffer cb) {
+        int iLenStartIndex = cb.writerIndex();
+        cb.writeByte(TYPE);
+        cb.writeByte(LENGTH);
+        cb.writeInt(rawValue);
+        return cb.writerIndex() - iLenStartIndex;
+    }
+
+    /**
+     * Reads the channel buffer and returns object of FourOctetAsNumCapabilityTlv.
+     * @param cb type of channel buffer
+     * @return object of FourOctetAsNumCapabilityTlv
+     */
+    public static FourOctetAsNumCapabilityTlv read(ChannelBuffer cb) {
+        return FourOctetAsNumCapabilityTlv.of(cb.readInt());
+    }
+
+    @Override
+    public String toString() {
+        return MoreObjects.toStringHelper(getClass())
+                .add("Type", TYPE)
+                .add("Length", LENGTH)
+                .add("Value", rawValue).toString();
+    }
+
+    @Override
+    public int compareTo(Object o) {
+        // TODO Auto-generated method stub
+        return 0;
+    }
+}
diff --git a/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/types/MultiProtocolExtnCapabilityTlv.java b/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/types/MultiProtocolExtnCapabilityTlv.java
index 465eb97..afbf4d9 100644
--- a/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/types/MultiProtocolExtnCapabilityTlv.java
+++ b/protocols/bgp/bgpio/src/main/java/org/onosproject/bgpio/types/MultiProtocolExtnCapabilityTlv.java
@@ -1,166 +1,166 @@
-/*
- * 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.bgpio.types;
-
-import com.google.common.base.MoreObjects;
-import org.jboss.netty.buffer.ChannelBuffer;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import java.util.Objects;
-
-/**
- * Provides MultiProtocolExtnCapabilityTlv.
- */
-public class MultiProtocolExtnCapabilityTlv implements BgpValueType {
-
-    /*
-        0       7       15      23      31
-        +-------+-------+-------+-------+
-        |  AFI          | Res   |  SAFI |
-        +-------+-------+-------+-------+
-
-        Multiprotocol Extensions CAPABILITY TLV format
-        REFERENCE : RFC 4760
-     */
-    protected static final Logger log = LoggerFactory
-            .getLogger(MultiProtocolExtnCapabilityTlv.class);
-
-    public static final byte TYPE = 1;
-    public static final byte LENGTH = 4;
-
-    private final short afi;
-    private final byte res;
-    private final byte safi;
-
-    /**
-     * Constructor to initialize variables.
-     * @param afi Address Family Identifiers
-     * @param res reserved field
-     * @param safi Subsequent Address Family Identifier
-     */
-    public MultiProtocolExtnCapabilityTlv(short afi, byte res, byte safi) {
-        this.afi = afi;
-        this.res = res;
-        this.safi = safi;
-    }
-
-    /**
-     * Returns object of MultiProtocolExtnCapabilityTlv.
-     * @param afi Address Family Identifiers
-     * @param res reserved field
-     * @param safi Subsequent Address Family Identifier
-     * @return object of MultiProtocolExtnCapabilityTlv
-     */
-    public static MultiProtocolExtnCapabilityTlv of(short afi, byte res,
-                                                    byte safi) {
-        return new MultiProtocolExtnCapabilityTlv(afi, res, safi);
-    }
-
-    /**
-     * Returns afi Address Family Identifiers value.
-     * @return afi Address Family Identifiers value
-     */
-    public short getAfi() {
-        return afi;
-    }
-
-    /**
-     * Returns res reserved field value.
-     * @return res reserved field value
-     */
-    public byte getRes() {
-        return res;
-    }
-
-    /**
-     * Returns safi Subsequent Address Family Identifier value.
-     * @return safi Subsequent Address Family Identifier value
-     */
-    public byte getSafi() {
-        return safi;
-    }
-
-    @Override
-    public short getType() {
-        return TYPE;
-    }
-
-    @Override
-    public int hashCode() {
-        return Objects.hash(afi, res, safi);
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-        if (obj instanceof MultiProtocolExtnCapabilityTlv) {
-            MultiProtocolExtnCapabilityTlv other = (MultiProtocolExtnCapabilityTlv) obj;
-            return Objects.equals(this.afi, other.afi)
-                    && Objects.equals(this.res, other.res)
-                    && Objects.equals(this.safi, other.safi);
-        }
-        return false;
-    }
-
-    @Override
-    public int write(ChannelBuffer cb) {
-        int iLenStartIndex = cb.writerIndex();
-        cb.writeByte(TYPE);
-        cb.writeByte(LENGTH);
-
-        // write afi
-        cb.writeShort(afi);
-
-        // write res
-        cb.writeByte(res);
-
-        // write safi
-        cb.writeByte(safi);
-
-        return cb.writerIndex() - iLenStartIndex;
-    }
-
-    /**
-     * Reads from channel buffer and returns object of MultiprotocolCapabilityTlv.
-     * @param cb of type channel buffer
-     * @return object of MultiProtocolExtnCapabilityTlv
-     */
-    public static BgpValueType read(ChannelBuffer cb) {
-        short afi = cb.readShort();
-        byte res = cb.readByte();
-        byte safi = cb.readByte();
-        return new MultiProtocolExtnCapabilityTlv(afi, res, safi);
-    }
-
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(getClass())
-                .add("Type", TYPE)
-                .add("Length", LENGTH)
-                .add("AFI", afi)
-                .add("Reserved", res)
-                .add("SAFI", safi).toString();
-    }
-
-    @Override
-    public int compareTo(Object o) {
-        // TODO Auto-generated method stub
-        return 0;
-    }
-}
+/*
+ * 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.bgpio.types;
+
+import com.google.common.base.MoreObjects;
+import org.jboss.netty.buffer.ChannelBuffer;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.Objects;
+
+/**
+ * Provides MultiProtocolExtnCapabilityTlv.
+ */
+public class MultiProtocolExtnCapabilityTlv implements BgpValueType {
+
+    /*
+        0       7       15      23      31
+        +-------+-------+-------+-------+
+        |  AFI          | Res   |  SAFI |
+        +-------+-------+-------+-------+
+
+        Multiprotocol Extensions CAPABILITY TLV format
+        REFERENCE : RFC 4760
+     */
+    protected static final Logger log = LoggerFactory
+            .getLogger(MultiProtocolExtnCapabilityTlv.class);
+
+    public static final byte TYPE = 1;
+    public static final byte LENGTH = 4;
+
+    private final short afi;
+    private final byte res;
+    private final byte safi;
+
+    /**
+     * Constructor to initialize variables.
+     * @param afi Address Family Identifiers
+     * @param res reserved field
+     * @param safi Subsequent Address Family Identifier
+     */
+    public MultiProtocolExtnCapabilityTlv(short afi, byte res, byte safi) {
+        this.afi = afi;
+        this.res = res;
+        this.safi = safi;
+    }
+
+    /**
+     * Returns object of MultiProtocolExtnCapabilityTlv.
+     * @param afi Address Family Identifiers
+     * @param res reserved field
+     * @param safi Subsequent Address Family Identifier
+     * @return object of MultiProtocolExtnCapabilityTlv
+     */
+    public static MultiProtocolExtnCapabilityTlv of(short afi, byte res,
+                                                    byte safi) {
+        return new MultiProtocolExtnCapabilityTlv(afi, res, safi);
+    }
+
+    /**
+     * Returns afi Address Family Identifiers value.
+     * @return afi Address Family Identifiers value
+     */
+    public short getAfi() {
+        return afi;
+    }
+
+    /**
+     * Returns res reserved field value.
+     * @return res reserved field value
+     */
+    public byte getRes() {
+        return res;
+    }
+
+    /**
+     * Returns safi Subsequent Address Family Identifier value.
+     * @return safi Subsequent Address Family Identifier value
+     */
+    public byte getSafi() {
+        return safi;
+    }
+
+    @Override
+    public short getType() {
+        return TYPE;
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(afi, res, safi);
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+        if (obj instanceof MultiProtocolExtnCapabilityTlv) {
+            MultiProtocolExtnCapabilityTlv other = (MultiProtocolExtnCapabilityTlv) obj;
+            return Objects.equals(this.afi, other.afi)
+                    && Objects.equals(this.res, other.res)
+                    && Objects.equals(this.safi, other.safi);
+        }
+        return false;
+    }
+
+    @Override
+    public int write(ChannelBuffer cb) {
+        int iLenStartIndex = cb.writerIndex();
+        cb.writeByte(TYPE);
+        cb.writeByte(LENGTH);
+
+        // write afi
+        cb.writeShort(afi);
+
+        // write res
+        cb.writeByte(res);
+
+        // write safi
+        cb.writeByte(safi);
+
+        return cb.writerIndex() - iLenStartIndex;
+    }
+
+    /**
+     * Reads from channel buffer and returns object of MultiprotocolCapabilityTlv.
+     * @param cb of type channel buffer
+     * @return object of MultiProtocolExtnCapabilityTlv
+     */
+    public static BgpValueType read(ChannelBuffer cb) {
+        short afi = cb.readShort();
+        byte res = cb.readByte();
+        byte safi = cb.readByte();
+        return new MultiProtocolExtnCapabilityTlv(afi, res, safi);
+    }
+
+    @Override
+    public String toString() {
+        return MoreObjects.toStringHelper(getClass())
+                .add("Type", TYPE)
+                .add("Length", LENGTH)
+                .add("AFI", afi)
+                .add("Reserved", res)
+                .add("SAFI", safi).toString();
+    }
+
+    @Override
+    public int compareTo(Object o) {
+        // TODO Auto-generated method stub
+        return 0;
+    }
+}
diff --git a/providers/bgp/cfg/src/main/java/org/onosproject/provider/bgp/cfg/impl/package-info.java b/providers/bgp/cfg/src/main/java/org/onosproject/provider/bgp/cfg/impl/package-info.java
index d9fc877..cc36490 100755
--- a/providers/bgp/cfg/src/main/java/org/onosproject/provider/bgp/cfg/impl/package-info.java
+++ b/providers/bgp/cfg/src/main/java/org/onosproject/provider/bgp/cfg/impl/package-info.java
@@ -1,20 +1,20 @@
-/*
- * 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.
- */
-
-/**
- *Bgp configuration provider.
- */
-package org.onosproject.provider.bgp.cfg.impl;
+/*
+ * 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.
+ */
+
+/**
+ *Bgp configuration provider.
+ */
+package org.onosproject.provider.bgp.cfg.impl;
diff --git a/tools/build/conf/src/main/resources/onos/checkstyle.xml b/tools/build/conf/src/main/resources/onos/checkstyle.xml
index 0a9772f..9765196 100644
--- a/tools/build/conf/src/main/resources/onos/checkstyle.xml
+++ b/tools/build/conf/src/main/resources/onos/checkstyle.xml
@@ -94,6 +94,12 @@
         <property name="message" value="Line has trailing spaces."/>
     </module>
 
+    <module name="RegexpMultiline">
+        <property name="format" value="\r\n"/>
+        <property name="maximum" value="0"/>
+        <property name="message" value="Line has windows line endings."/>
+    </module>
+
     <!-- Checks for Headers                                -->
     <!-- See http://checkstyle.sf.net/config_header.html   -->
     <!-- <module name="Header"> -->
diff --git a/utils/misc/src/main/java/org/onlab/util/HexDump.java b/utils/misc/src/main/java/org/onlab/util/HexDump.java
index b40cf6e..fdb696b 100755
--- a/utils/misc/src/main/java/org/onlab/util/HexDump.java
+++ b/utils/misc/src/main/java/org/onlab/util/HexDump.java
@@ -1,54 +1,54 @@
-/*
- * 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.onlab.util;
-
-import org.jboss.netty.buffer.ChannelBuffer;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-/**
- * HexDump class an utility to dump buffer in hex format.
- */
-public final class HexDump {
-    protected static final Logger log = LoggerFactory.getLogger(HexDump.class);
-
-    private HexDump() {
-    }
-
-    /**
-     * Dump the buffer content in hex format.
-     *
-     * @param buff buffer content to dump in hex format
-     */
-    public static void dump(ChannelBuffer buff) {
-        buff.markReaderIndex();
-        try {
-            do {
-                StringBuilder sb = new StringBuilder();
-                for (int k = 0; (k < 16) && (buff.readableBytes() != 0); ++k) {
-                    if (0 == k % 4) {
-                        sb.append(String.format(" ")); // blank after 4 bytes
-                    }
-                    sb.append(String.format("%02X ", buff.readByte()));
-                }
-                log.debug(sb.toString());
-            } while (buff.readableBytes() != 0);
-        } catch (Exception e) {
-            log.error("[HexDump] Invalid buffer: " + e.toString());
-        }
-        buff.resetReaderIndex();
-    }
-}
+/*
+ * 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.onlab.util;
+
+import org.jboss.netty.buffer.ChannelBuffer;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * HexDump class an utility to dump buffer in hex format.
+ */
+public final class HexDump {
+    protected static final Logger log = LoggerFactory.getLogger(HexDump.class);
+
+    private HexDump() {
+    }
+
+    /**
+     * Dump the buffer content in hex format.
+     *
+     * @param buff buffer content to dump in hex format
+     */
+    public static void dump(ChannelBuffer buff) {
+        buff.markReaderIndex();
+        try {
+            do {
+                StringBuilder sb = new StringBuilder();
+                for (int k = 0; (k < 16) && (buff.readableBytes() != 0); ++k) {
+                    if (0 == k % 4) {
+                        sb.append(String.format(" ")); // blank after 4 bytes
+                    }
+                    sb.append(String.format("%02X ", buff.readByte()));
+                }
+                log.debug(sb.toString());
+            } while (buff.readableBytes() != 0);
+        } catch (Exception e) {
+            log.error("[HexDump] Invalid buffer: " + e.toString());
+        }
+        buff.resetReaderIndex();
+    }
+}
