diff --git a/minindn/helpers/__init__.py b/minindn/helpers/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/minindn/helpers/__init__.py
diff --git a/minindn/helpers/experiment.py b/minindn/helpers/experiment.py
new file mode 100644
index 0000000..226684e
--- /dev/null
+++ b/minindn/helpers/experiment.py
@@ -0,0 +1,107 @@
+# -*- Mode:python; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
+#
+# Copyright (C) 2015-2019, The University of Memphis,
+#                          Arizona Board of Regents,
+#                          Regents of the University of California.
+#
+# This file is part of Mini-NDN.
+# See AUTHORS.md for a complete list of Mini-NDN authors and contributors.
+#
+# Mini-NDN is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# Mini-NDN is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with Mini-NDN, e.g., in COPYING.md file.
+# If not, see <http://www.gnu.org/licenses/>.
+
+import time
+import sys
+from itertools import cycle
+
+from mininet.log import info
+
+from minindn.helpers.nfdc import Nfdc
+from minindn.helpers.ndnpingclient import NDNPingClient
+
+class Experiment(object):
+    @staticmethod
+    def checkConvergence(ndn, hosts, convergenceTime, quit=False):
+        # Wait for convergence time period
+        info('Waiting {} seconds for convergence...\n'.format(convergenceTime))
+        time.sleep(convergenceTime)
+        info('...done\n')
+
+        # To check whether all the nodes of NLSR have converged
+        didNlsrConverge = True
+
+        # Checking for convergence
+        for host in hosts:
+            statusRouter = host.cmd('nfdc fib list | grep site/%C1.Router/cs/')
+            statusPrefix = host.cmd('nfdc fib list | grep ndn | grep site | grep -v Router')
+            didNodeConverge = True
+            for node in hosts:
+                # Node has its own router name in the fib list, but not name prefix
+                if (('/ndn/{}-site/%C1.Router/cs/{}'.format(node.name, node.name)) not in statusRouter or
+                      host.name != node.name and ('/ndn/{}-site/{}'.format(node.name, node.name)) not in statusPrefix):
+                    didNodeConverge = False
+                    didNlsrConverge = False
+
+            host.cmd('echo {} > convergence-result &'.format(didNodeConverge))
+
+        if not didNlsrConverge:
+            info('NLSR has not converged. Exiting...\n')
+            if quit:
+                ndn.stop()
+                sys.exit(1)
+        else:
+            info('NLSR has converged successfully.\n')
+
+        return didNlsrConverge
+
+    @staticmethod
+    def setupPing(hosts, strategy):
+        for host in hosts:
+            host.cmd('mkdir -p ping-data')
+            Nfdc.setStrategy(host, '/ndn/', strategy)
+            host.cmd('ndnpingserver /ndn/{}-site/{} > ping-server &'.format(host.name, host.name))
+
+    @staticmethod
+    def startPctPings(net, nPings, pctTraffic=1.0):
+        nNodesToPing = int(round(len(net.hosts) * pctTraffic))
+        info('Each node will ping {} node(s)\n'.format(nNodesToPing))
+        # Temporarily store all the nodes being pinged by a particular node
+        nodesPingedList = []
+        pingedDict = {}
+
+        for host in net.hosts:
+            # Create a circular list
+            pool = cycle(net.hosts)
+
+            # Move iterator to current node
+            next(x for x in pool if host.name == x.name)
+
+            # Track number of nodes to ping scheduled for this node
+            nNodesScheduled = 0
+
+            while nNodesScheduled < nNodesToPing:
+                other = next(pool)
+
+                # Do not ping self
+                if host.name != other.name:
+                    NDNPingClient.ping(host, other, nPings)
+                    nodesPingedList.append(other)
+
+                # Always increment because in 100% case a node should not ping itself
+                nNodesScheduled = nNodesScheduled + 1
+
+            pingedDict[host] = nodesPingedList
+            nodesPingedList = []
+
+        return pingedDict
diff --git a/minindn/helpers/ip_routing_helper.py b/minindn/helpers/ip_routing_helper.py
new file mode 100644
index 0000000..8c2bddf
--- /dev/null
+++ b/minindn/helpers/ip_routing_helper.py
@@ -0,0 +1,134 @@
+# -*- Mode:python; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
+#
+# Copyright (C) 2015-2019, The University of Memphis,
+#                          Arizona Board of Regents,
+#                          Regents of the University of California.
+#
+# This file is part of Mini-NDN.
+# See AUTHORS.md for a complete list of Mini-NDN authors and contributors.
+#
+# Mini-NDN is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# Mini-NDN is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with Mini-NDN, e.g., in COPYING.md file.
+# If not, see <http://www.gnu.org/licenses/>.
+
+from igraph import Graph
+from mininet.log import info
+
+class LinkInfo(object):
+    """
+    This class is used to encapsule link information (IP and interface names).
+    """
+
+    def __init__(self, start_intf_name, start_ip, end_intf_name, end_ip):
+        self.start_intf_name = start_intf_name
+        self.start_intf_ip = start_ip
+        self.end_intf_name = end_intf_name
+        self.end_ip = end_ip
+
+class IPRoutingHelper(object):
+    """The routing helper allows to run IP-based evaluations with Mini-NDN. It configures static IP
+    routes to all nodes, which means that all nodes can reach all other nodes in the network
+    reachable, even when relaying is required.
+
+     Usage from Experiment folder: `IPRoutingHelper.calcAllRoutes(self.net)`
+    """
+
+    @staticmethod
+    def findLinkInformation(links, first_node, second_node):
+        """ This method returns link information of a link connecting two nodes.
+
+        :param links: All links in the emulation topology
+        :param first_node: Current node which is looked at
+        :param second_node: Target node (neighbour  of first_node)
+        :return: Link information as LinkInfo object, or returns null None if the
+            nodes are not directly connected
+        """
+        for link in links:
+            if link.intf1.node.name == first_node and link.intf2.node.name == second_node:
+                return LinkInfo(link.intf1.name, link.intf1.ip, link.intf2.name, link.intf2.ip)
+            elif link.intf2.node.name == first_node and link.intf1.node.name == second_node:
+                return LinkInfo(link.intf2.name, link.intf2.ip, link.intf1.name, link.intf1.ip)
+
+        return None
+
+    @staticmethod
+    def calcAllRoutes(net):
+        """ Configures IP routes between all nodes in the emulation topology. This is done in three
+         steps:
+
+        1) IP forwarding is enabled on all nodes
+        2) The igraph lib is used to calculate all shortest paths between the nodes
+        3) Route add commands are used to actually configure the ip routes
+
+        :param net:
+        """
+
+        mini_nodes = net.hosts
+        mini_links = net.links
+
+        # Enabling IP forwaring on all nodes
+        info('Configure IP forwarding on all nodes\n')
+        for node in mini_nodes:
+            node.cmd('sysctl -w net.ipv4.ip_forward=1')
+
+        # Calculate igraph to calculate all shortest paths between nodes
+        node_names = [node.name for node in mini_nodes]
+        links = []
+        for link in mini_links:
+            links.append((link.intf1.node.name, link.intf2.node.name))
+            links.append((link.intf2.node.name, link.intf1.node.name))
+
+        networkGraph = Graph()
+        networkGraph = networkGraph.as_directed()
+        for node in node_names:
+            networkGraph.add_vertex(node)
+        for (a, b) in links:
+            networkGraph.add_edges([(a, b), (b, a)])
+
+        named_paths = []
+        for from_node in node_names:
+            for to_node in node_names:
+                if from_node != to_node:
+                    paths = networkGraph.get_all_shortest_paths(from_node, to_node)
+                    if len(paths) == 0:
+                        continue
+                    shortest_path = paths[0]
+                    shortest_path_with_nodenames = []
+                    for node in shortest_path:
+                        shortest_path_with_nodenames.append(networkGraph.vs['name'][node])
+                    named_paths.append(shortest_path_with_nodenames)
+
+        # Iterate over all paths and configure the routes using the 'route add'
+        info('Configure routes on all nodes\n')
+        for path in named_paths:
+            start_node = path[0]
+            end_node = path[-1]
+            mini_start = net.get(start_node)
+            mini_end = net.get(end_node)
+
+            link_info = IPRoutingHelper.findLinkInformation(mini_links, path[0], path[1])
+            start_intf = link_info.start_intf_name
+
+            for intf in mini_end.intfs:
+                addr = mini_end.intfs[intf].ip
+                if len(path) == 2:
+                    # For direct connection, configure exit interface
+                    info('[{}] route add -host {} dev {}\n'.format(start_node, addr, start_intf))
+                    mini_start.cmd('route add -host {} dev {}'.format(addr, start_intf))
+                elif len(path) > 2:
+                    # For longer paths, configure next hop as gateway
+                    gateway_ip = link_info.end_ip
+                    info('[{}] route add -host {} dev {} gw {}\n'
+                         .format(start_node, addr, start_intf, gateway_ip))
+                    mini_start.cmd('route add -host {} dev {} gw {}'
+                                   .format(addr, start_intf, gateway_ip))
diff --git a/minindn/helpers/ndn_routing_helper.py b/minindn/helpers/ndn_routing_helper.py
new file mode 100644
index 0000000..38d841a
--- /dev/null
+++ b/minindn/helpers/ndn_routing_helper.py
@@ -0,0 +1,370 @@
+ # -*- Mode:python; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
+#
+# Copyright (C) 2015-2019, The University of Memphis
+#
+# This file is part of Mini-NDN.
+# See AUTHORS.md for a complete list of Mini-NDN authors and contributors.
+#
+# Mini-NDN is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# Mini-NDN is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with Mini-NDN, e.g., in COPYING.md file.
+# If not, see <http://www.gnu.org/licenses/>.
+
+# IMPORTANT! This feature is in highly experimental phase and may go several changes
+# in future
+
+'''
+This module will compute link state, hyperbolic and geohyperbolic
+routes and their costs from the given Mini-NDN topology
+'''
+
+import heapq
+from math import sin, cos, sinh, cosh, acos, acosh
+import json
+import operator
+from collections import defaultdict
+
+from mininet.log import info, debug, error, warn
+from minindn.helpers.nfdc import Nfdc as nfdc
+
+UNKNOWN_DISTANCE = -1
+HYPERBOLIC_COST_ADJUSTMENT_FACTOR = 1000
+
+def dijkstra(graph, start, end, ignoredNode=None):
+    """
+    Compute shortest path and cost from a given source to a destination
+    using Dijkstra algorithm
+
+    :param Graph graph: given network topology/graph
+    :param Start start: source node in a given network graph/topology
+    :end End end: destination node in a given network graph/topology
+    :param Node ignoredNode: node to ignore computing shortest path from
+    """
+    queue = [(0, start, [])]
+    seen = set()
+    while True:
+        (cost, v, path) = heapq.heappop(queue)
+        if v not in seen:
+            path = path + [v]
+            seen.add(v)
+            if v == end:
+                debug("Distance from {} to {} is {}".format(start, end, cost))
+                return cost, path
+            for (_next, c) in graph[v].items():
+                if _next != ignoredNode: # Ignore path going via ignoreNode
+                    heapq.heappush(queue, (cost + c, _next, path))
+
+        if not queue: # return if no path exist from source - destination except via ignoreNode
+            debug("Distance from {} to {} is {}".format(start, end, cost))
+            return cost, None
+
+def calculateAngularDistance(angleVectorI, angleVectorJ):
+    """
+    For hyperbolic/geohyperbolic routing algorithm, this function computes angular distance between
+    two nodes. A node can have two or more than two angular coordinates.
+
+    :param AngleVectorI angleVectorI: list of angular coordinate of a give node I
+    :param AngleVectorJ angleVectorJ: list of angular coordinate of a give node J
+
+    ref: https://en.wikipedia.org/wiki/N-sphere#Spherical_coordinates
+
+    """
+    innerProduct = 0.0
+    if len(angleVectorI) != len(angleVectorJ):
+        error("Angle vector sizes do not match")
+        return UNKNOWN_DISTANCE
+
+    # Calculate x0 of the vectors
+    x0i = cos(angleVectorI[0])
+    x0j = cos(angleVectorJ[0])
+
+    # Calculate xn of the vectors
+    xni = sin(angleVectorI[len(angleVectorI) - 1])
+    xnj = sin(angleVectorJ[len(angleVectorJ) - 1])
+
+    # Do the aggregation of the (n-1) coordinates (if there is more than one angle)
+    # i.e contraction of all (n-1)-dimensional angular coordinates to one variable
+    for k in range(0, len(angleVectorI)-1):
+        xni *= sin(angleVectorI[k])
+        xnj *= sin(angleVectorJ[k])
+
+    innerProduct += (x0i * x0j) + (xni * xnj)
+
+    if len(angleVectorI) > 1:
+        for m in range(1, len(angleVectorI)):
+            # Calculate euclidean coordinates given the angles and assuming R_sphere = 1
+            xmi = cos(angleVectorI[m])
+            xmj = cos(angleVectorJ[m])
+            for l in range(0, m):
+                xmi *= sin(angleVectorI[l])
+                xmj *= sin(angleVectorJ[l])
+
+        innerProduct += xmi * xmj
+
+    # ArcCos of the inner product gives the angular distance
+    # between two points on a d-dimensional sphere
+    angularDist = acos(innerProduct)
+    debug("Angular distance from {} to {} is {}".format(angleVectorI, angleVectorJ, angularDist))
+    return angularDist
+
+def getHyperbolicDistance(sourceNode, destNode):
+    """
+    Return hyperbolic or geohyperbolic distance between two nodes. The distance is computed
+    on the basis of following algorithm/mathematics
+    ref: https://en.wikipedia.org/wiki/Hyperbolic_geometry
+    """
+    r1 = [key for key in sourceNode][0]
+    r2 = [key for key in destNode][0]
+
+    zeta = 1.0
+    dtheta = calculateAngularDistance(sourceNode[r1], destNode[r2])
+    hyperbolicDistance = (1./zeta) * acosh(cosh(zeta * r1) * cosh(zeta * r2) -\
+                                           sinh(zeta * r1) * sinh(zeta * r2) * cos(dtheta))
+
+    debug("Distance from {} to {} is {}".format(sourceNode, destNode, hyperbolicDistance))
+    return hyperbolicDistance
+
+class _CalculateRoutes(object):
+    """
+    Creates a route calculation object, which is used to compute routes from a node to
+    every other nodes in a given topology topology using hyperbolic or geohyperbolic
+    routing algorithm
+
+    :param NetObject netObj: Mininet net object
+    :param RoutingType routingType: (optional) Routing algorithm, link-state or hr etc
+    """
+    def __init__(self, netObj, routingType):
+        self.adjacenctMatrix = defaultdict(dict)
+        self.nodeDict = defaultdict(dict)
+        self.routingType = routingType
+        for host in netObj.hosts:
+            if 'radius' in host.params['params']:
+                radius = float(host.params['params']['radius'])
+            else:
+                radius = 0.0
+            if 'angles' in host.params['params']:
+                angles = [float(x) for x in host.params['params']['angle'].split(',')]
+            else:
+                angles = 0.0
+            self.nodeDict[host.name][radius] = angles
+
+        for link in netObj.topo.links(withInfo=True):
+            linkDelay = int(link[2]['delay'].replace("ms", ""))
+            self.adjacenctMatrix[link[0]][link[1]] = linkDelay
+            self.adjacenctMatrix[link[1]][link[0]] = linkDelay
+
+    def getNestedDictionary(self):
+        return defaultdict(self.getNestedDictionary)
+
+    def getRoutes(self, nFaces):
+        resultMatrix = self.getNestedDictionary()
+        routes = defaultdict(list)
+
+        if self.routingType == "link-state":
+            if nFaces == 1:
+                resultMatrix = self.computeDijkastra() # only best routes.
+            else:
+                resultMatrix = self.computeDijkastraAll() # all possible routes
+        elif self.routingType == "hr":
+            # Note: For hyperbolic, only way to find the best routes is by computing all possible
+            # routes and getting the best one.
+            resultMatrix = self.computeHyperbolic()
+        else:
+            info("Routing type not supported\n")
+            return []
+
+        for node in resultMatrix:
+            for destinationNode in resultMatrix[node]:
+                # Sort node - destination via neighbor based on their cost
+                tempDict = resultMatrix[node][destinationNode]
+                shortedTempDict = sorted(tempDict.items(), key=operator.itemgetter(1))
+                # nFaces option gets n-best faces based on shortest distance, default is all
+                if nFaces == 0:
+                    for item in shortedTempDict:
+                        viaNeighbor = item[0]
+                        cost = item[1]
+                        routes[node].append([destinationNode, str(cost), viaNeighbor])
+                else:
+                    for index, item in enumerate(shortedTempDict):
+                        if index >= nFaces:
+                            break
+                        viaNeighbor = item[0]
+                        cost = item[1]
+                        routes[node].append([destinationNode, str(cost), viaNeighbor])
+
+        debug("-routes----", routes)
+        return routes
+
+    def getNodeNames(self):
+        return [k for k in self.nodeDict]
+
+    def computeHyperbolic(self):
+        paths = self.getNestedDictionary()
+        nodeNames = self.getNodeNames()
+        for node in self.nodeDict:
+            neighbors = [k for k in self.adjacenctMatrix[node]]
+            for viaNeighbor in neighbors:
+                others = list(set(nodeNames) - set(viaNeighbor) - set(node))
+                paths[node][viaNeighbor][viaNeighbor] = 0
+                # Compute distance from neighbors to no-neighbors
+                for destinationNode in others:
+                    hyperbolicDistance = getHyperbolicDistance(self.nodeDict[viaNeighbor],
+                                                               self.nodeDict[destinationNode])
+                    hyperbolicCost = int(HYPERBOLIC_COST_ADJUSTMENT_FACTOR \
+                                         * round(hyperbolicDistance, 6))
+                    paths[node][destinationNode][viaNeighbor] = hyperbolicCost
+
+        debug("Shortest Distance Matrix: {}".format(json.dumps(paths)))
+        return paths
+
+    def computeDijkastra(self):
+        """
+        Dijkstra computation: Compute all the shortest paths from nodes to the destinations.
+        And fills the distance matrix with the corresponding source to destination cost
+        """
+        distanceMatrix = self.getNestedDictionary()
+        nodeNames = self.getNodeNames()
+        for node in nodeNames:
+            others = list(set(nodeNames) - set(node))
+            for destinationNode in others:
+                cost, path = dijkstra(self.adjacenctMatrix, node, destinationNode)
+                viaNeighbor = path[1]
+                distanceMatrix[node][destinationNode][viaNeighbor] = cost
+
+        debug("Shortest Distance Matrix: {}".format(json.dumps(distanceMatrix)))
+        return distanceMatrix
+
+    def computeDijkastraAll(self):
+        """
+        Multi-path Dijkastra computation: Compute all the shortest paths from nodes to the
+        destinations via all of its neighbors individually. And fills the distanceMatrixViaNeighbor
+        with a corresponding source to its destination cost
+
+        Important: distanceMatrixViaNeighbor represents the shortest distance from a source to a
+        destination via specific neighbors
+        """
+        distanceMatrixViaNeighbor = self.getNestedDictionary()
+        nodeNames = self.getNodeNames()
+        for node in nodeNames:
+            neighbors = [k for k in self.adjacenctMatrix[node]]
+            for viaNeighbor in neighbors:
+                directCost = self.adjacenctMatrix[node][viaNeighbor]
+                distanceMatrixViaNeighbor[node][viaNeighbor][viaNeighbor] = directCost
+                others = list(set(nodeNames) - set(viaNeighbor) - set(node))
+                for destinationNode in others:
+                    nodeNeighborCost = self.adjacenctMatrix[node][viaNeighbor]
+                    # path variable is not used for now
+                    cost, path = dijkstra(self.adjacenctMatrix, viaNeighbor, destinationNode, node)
+                    if cost != 0 and path != None:
+                        totalCost = cost + nodeNeighborCost
+                        distanceMatrixViaNeighbor[node][destinationNode][viaNeighbor] = totalCost
+
+        debug("Shortest Distance Matrix: {}".format(json.dumps(distanceMatrixViaNeighbor)))
+        return distanceMatrixViaNeighbor
+
+class NdnRoutingHelper(object):
+    """
+    This module is a helper class which helps to create face and register routes
+    to NFD from a given node to all of its neighbors.
+
+    :param NetObject netObject: Mininet net object
+    :param FaceType faceType: UDP, Ethernet etc.
+    :param Routing routingType: (optional) Routing algorithm, link-state or hr etc
+
+    """
+    def __init__(self, netObject, faceType=nfdc.PROTOCOL_UDP, routingType="link-state"):
+        self.net = netObject
+        self.faceType = faceType
+        self.routingType = routingType
+        self.routes = []
+        self.namePrefixes = {host_name.name: [] for host_name in self.net.hosts}
+        self.routeObject = _CalculateRoutes(self.net, self.routingType)
+
+    def globalRoutingHelperHandler(self):
+        for host in self.net.hosts:
+            neighborIPs = self.getNeighbor(host)
+            self.createFaces(host, neighborIPs)
+            self.routeAdd(host, neighborIPs)
+
+        info('Processed all the routes to NFD\n')
+
+    def addOrigin(self, nodes, prefix):
+        """
+        Add prefix/s as origin on node/s
+
+        :param Prefix prefix: Prefix that is originated by node/s (as producer) for this prefix
+        :param Nodes nodes: List of nodes from net object
+        """
+        for node in nodes:
+            self.namePrefixes[node.name] = prefix
+
+    def calculateNPossibleRoutes(self, nFaces=0):
+        """
+        By default, calculates all possible routes i.e. routes via all the faces of a node.
+        pass nFaces if want to compute routes via n number of faces. e.g. 2. For larger topology
+        the computation might take huge amount of time.
+
+        :param int nFaces: (optional) number of faces to consider while computing routes. Default
+          i.e. nFaces = 0 will compute all possible routes
+
+        """
+        self.routes = self.routeObject.getRoutes(nFaces)
+        if self.routes:
+            self.globalRoutingHelperHandler()
+        else:
+            warn("Route computation failed\n")
+
+    def calculateRoutes(self):
+        # Calculate shortest path for every node
+        self.calculateNPossibleRoutes(nFaces=1)
+
+    def createFaces(self, node, neighborIPs):
+        for ip in neighborIPs.values():
+            nfdc.createFace(node, ip, self.faceType)
+
+    def routeAdd(self, node, neighborIPs):
+        """
+        Add route from a node to its neighbors for each prefix/s  advertised by destination node
+
+        :param Node node: source node (Mininet net.host)
+        :param IP neighborIPs: IP addresses of neighbors
+        """
+        neighbors = self.routes[node.name]
+        for route in neighbors:
+            destination = route[0]
+            cost = int(route[1])
+            nextHop = route[2]
+            defaultPrefix = "/ndn/{}-site/{}".format(destination, destination)
+            prefixes = [defaultPrefix] + self.namePrefixes[destination]
+            for prefix in prefixes:
+                # Register routes to all the available destination name prefix/s
+                nfdc.registerRoute(node, prefix, neighborIPs[nextHop], \
+                                   nfdc.PROTOCOL_UDP, cost=cost)
+    @staticmethod
+    def getNeighbor(node):
+        # Nodes to IP mapping
+        neighborIPs = defaultdict()
+        for intf in node.intfList():
+            link = intf.link
+            if link:
+                node1, node2 = link.intf1.node, link.intf2.node
+
+                if node1 == node:
+                    other = node2
+                    ip = other.IP(str(link.intf2))
+                else:
+                    other = node1
+                    ip = other.IP(str(link.intf1))
+
+                # Used later to create faces
+                neighborIPs[other.name] = ip
+        return neighborIPs
diff --git a/minindn/helpers/ndnpingclient.py b/minindn/helpers/ndnpingclient.py
new file mode 100644
index 0000000..8220a2d
--- /dev/null
+++ b/minindn/helpers/ndnpingclient.py
@@ -0,0 +1,45 @@
+# -*- Mode:python; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
+#
+# Copyright (C) 2015-2019, The University of Memphis,
+#                          Arizona Board of Regents,
+#                          Regents of the University of California.
+#
+# This file is part of Mini-NDN.
+# See AUTHORS.md for a complete list of Mini-NDN authors and contributors.
+#
+# Mini-NDN is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# Mini-NDN is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with Mini-NDN, e.g., in COPYING.md file.
+# If not, see <http://www.gnu.org/licenses/>.
+
+import time
+
+# Todo: convert to app
+
+class NDNPingClient(object):
+    @staticmethod
+    def ping(source, dest, nPings=1, interval=None, timeout=None, starting_seq_num=None,
+             identifier=None, allow_stale_data=False, print_timestamp=True, sleepTime=0.2):
+        print('Scheduling ping(s) from {} to {}'.format(source.name, dest.name))
+        # Use '&' to run in background and perform parallel pings
+        source.cmd('ndnping{1}{2}{3}{4}{5}{6}{7} /ndn/{0}-site/{0} >> ping-data/{0}.txt &'
+        .format(
+            dest,
+            ' -c {}'.format(nPings),
+            ' -i {}'.format(interval) if interval else '',
+            ' -o {}'.format(timeout) if timeout  else '',
+            ' -n {}'.format(starting_seq_num) if starting_seq_num else '',
+            ' -p {}'.format(identifier) if identifier else '',
+            ' -a' if allow_stale_data else '',
+            ' -t' if print_timestamp else ''
+        ))
+        time.sleep(sleepTime)
diff --git a/minindn/helpers/nfdc.py b/minindn/helpers/nfdc.py
new file mode 100644
index 0000000..4a9ebf2
--- /dev/null
+++ b/minindn/helpers/nfdc.py
@@ -0,0 +1,85 @@
+# -*- Mode:python; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
+#
+# Copyright (C) 2015-2019, The University of Memphis,
+#                          Arizona Board of Regents,
+#                          Regents of the University of California.
+#
+# This file is part of Mini-NDN.
+# See AUTHORS.md for a complete list of Mini-NDN authors and contributors.
+#
+# Mini-NDN is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# Mini-NDN is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with Mini-NDN, e.g., in COPYING.md file.
+# If not, see <http://www.gnu.org/licenses/>.
+
+from mininet.log import debug
+from minindn.minindn import Minindn
+
+SLEEP_TIME = 0.2
+
+class Nfdc(object):
+    STRATEGY_ASF = 'asf'
+    STRATEGY_BEST_ROUTE = 'best-route'
+    STRATEGY_MULTICAST = 'multicast'
+    STRATEGY_NCC = 'ncc'
+    PROTOCOL_UDP = 'udp'
+    PROTOCOL_TCP = 'tcp'
+    PROTOCOL_ETHER = 'ether'
+
+    @staticmethod
+    def registerRoute(node, namePrefix, remoteNodeAddress, protocol=PROTOCOL_UDP, origin=255,
+                      cost=0, inheritFlag=True, captureFlag=False, expirationInMillis=None):
+        cmd = ('nfdc route add {} {}://{} origin {} cost {} {}{}').format(
+            namePrefix,
+            protocol,
+            remoteNodeAddress,
+            origin,
+            cost,
+            'no-inherit ' if not inheritFlag else '',
+            'capture ' if captureFlag else '',
+            'expires {}'.format(expirationInMillis) if expirationInMillis else ''
+        )
+
+        debug(node.cmd(cmd))
+        Minindn.sleep(SLEEP_TIME)
+
+    @staticmethod
+    def unregisterRoute(node, namePrefix, remoteNodeAddress, origin=255):
+        cmd = 'nfdc route remove {} {} {}'.format(namePrefix, remoteNodeAddress, origin)
+        debug(node.cmd(cmd))
+        Minindn.sleep(SLEEP_TIME)
+
+    @staticmethod
+    def createFace(node, remoteNodeAddress, protocol='udp', isPermanent=False):
+        cmd = ('nfdc face create {}://{} {}'.format(
+            protocol,
+            remoteNodeAddress,
+            'permanent' if isPermanent else 'persistent'
+        ))
+        debug(node.cmd(cmd))
+        Minindn.sleep(SLEEP_TIME)
+
+    @staticmethod
+    def destroyFace(node, remoteNodeAddress, protocol='udp'):
+        debug(node.cmd('nfdc face destroy {}://{}'.format(protocol, remoteNodeAddress)))
+        Minindn.sleep(SLEEP_TIME)
+
+    @staticmethod
+    def setStrategy(node, namePrefix, strategy):
+        cmd = 'nfdc strategy set {} ndn:/localhost/nfd/strategy/{}'.format(namePrefix, strategy)
+        debug(node.cmd(cmd))
+        Minindn.sleep(SLEEP_TIME)
+
+    @staticmethod
+    def unsetStrategy(node, namePrefix):
+        debug(node.cmd("nfdc strategy unset {}".format(namePrefix)))
+        Minindn.sleep(SLEEP_TIME)
diff --git a/minindn/helpers/process_monitor.py b/minindn/helpers/process_monitor.py
new file mode 100644
index 0000000..4fa3738
--- /dev/null
+++ b/minindn/helpers/process_monitor.py
@@ -0,0 +1,52 @@
+# -*- Mode:python; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
+#
+# Copyright (C) 2015-2019, The University of Memphis,
+#                          Arizona Board of Regents,
+#                          Regents of the University of California.
+#
+# This file is part of Mini-NDN.
+# See AUTHORS.md for a complete list of Mini-NDN authors and contributors.
+#
+# Mini-NDN is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# Mini-NDN is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with Mini-NDN, e.g., in COPYING.md file.
+# If not, see <http://www.gnu.org/licenses/>.
+
+import time
+
+from threading import Timer
+
+class ProcessMonitor(object):
+    def __init__(self, processId, processName, outputDir, interval=1):
+        self._processId = processId.strip()
+        self._processName = processName
+        self._statFile = '/proc/{}/stat'.format(self._processId)
+        self._logFile = '{}/{}-{}-stat.txt'.format(outputDir, self._processName, self._processId)
+        self._interval = interval
+
+    def _recordStats(self):
+        try:
+            with open(self._statFile, 'r') as stat:
+                currentTime = int(time.time())
+                with open(self._logFile, 'a') as log:
+                    for line in stat:
+                        log.write('{} {}'.format(currentTime, line))
+        except IOError as e:
+            print('I/O error({0}): {1}'.format(e.errno, e.strerror))
+            print('No process with PID={}'.format(self._processId))
+            return
+
+        self.start() # Reschedule event
+
+    def start(self):
+        self._timer = Timer(self._interval, self._recordStats)
+        self._timer.start()
