diff --git a/incubator/net/src/main/java/org/onosproject/incubator/net/virtual/impl/PtToPtIntentVirtualNetworkProvider.java b/incubator/net/src/main/java/org/onosproject/incubator/net/virtual/impl/PtToPtIntentVirtualNetworkProvider.java
deleted file mode 100644
index d5b049c..0000000
--- a/incubator/net/src/main/java/org/onosproject/incubator/net/virtual/impl/PtToPtIntentVirtualNetworkProvider.java
+++ /dev/null
@@ -1,208 +0,0 @@
-/*
- * Copyright 2016-present 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.incubator.net.virtual.impl;
-
-
-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.core.ApplicationId;
-import org.onosproject.core.CoreService;
-import org.onosproject.incubator.net.tunnel.TunnelId;
-import org.onosproject.incubator.net.virtual.DefaultVirtualLink;
-import org.onosproject.incubator.net.virtual.NetworkId;
-import org.onosproject.incubator.net.virtual.VirtualNetworkProvider;
-import org.onosproject.incubator.net.virtual.VirtualNetworkProviderRegistry;
-import org.onosproject.incubator.net.virtual.VirtualNetworkProviderService;
-import org.onosproject.net.ConnectPoint;
-import org.onosproject.net.EncapsulationType;
-import org.onosproject.net.intent.Constraint;
-import org.onosproject.net.intent.Intent;
-import org.onosproject.net.intent.IntentEvent;
-import org.onosproject.net.intent.IntentListener;
-import org.onosproject.net.intent.IntentService;
-import org.onosproject.net.intent.Key;
-import org.onosproject.net.intent.PointToPointIntent;
-import org.onosproject.net.intent.constraint.EncapsulationConstraint;
-import org.onosproject.net.provider.AbstractProvider;
-import org.slf4j.Logger;
-
-import java.util.ArrayList;
-import java.util.List;
-import java.util.StringTokenizer;
-
-import static com.google.common.base.Preconditions.checkNotNull;
-import static org.slf4j.LoggerFactory.getLogger;
-
-/**
- * Point to point intent VirtualNetworkProvider implementation.
- */
-@Component(immediate = true)
-@Service
-public class PtToPtIntentVirtualNetworkProvider extends AbstractProvider
-        implements VirtualNetworkProvider {
-
-    private final Logger log = getLogger(PtToPtIntentVirtualNetworkProvider.class);
-    private static final String NETWORK_ID_NULL = "Network ID cannot be null";
-    private static final String CONNECT_POINT_NULL = "Connect Point cannot be null";
-    private static final String INTENT_NULL = "Intent cannot be null";
-    private static final String NETWORK_ID = "networkId=";
-    protected static final String KEY_FORMAT = NETWORK_ID + "%s, src=%s, dst=%s";
-    private static final int MAX_WAIT_COUNT = 30;
-
-    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
-    protected VirtualNetworkProviderRegistry providerRegistry;
-
-    private VirtualNetworkProviderService providerService;
-
-    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
-    protected IntentService intentService;
-
-    private final InternalPtPtIntentListener intentListener = new InternalPtPtIntentListener();
-
-    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
-    protected CoreService coreService;
-
-    protected static final String PTPT_INTENT_APPID = "org.onosproject.vnet.intent";
-    private ApplicationId appId;
-
-    /**
-     * Default constructor.
-     */
-    public PtToPtIntentVirtualNetworkProvider() {
-        super(DefaultVirtualLink.PID);
-    }
-
-    @Activate
-    public void activate() {
-        providerService = providerRegistry.register(this);
-        appId = coreService.registerApplication(PTPT_INTENT_APPID);
-
-        intentService.addListener(intentListener);
-        log.info("Started");
-    }
-
-    @Deactivate
-    public void deactivate() {
-        intentService.removeListener(intentListener);
-        providerRegistry.unregister(this);
-        providerService = null;
-        log.info("Stopped");
-    }
-
-    @Override
-    public boolean isTraversable(ConnectPoint src, ConnectPoint dst) {
-        return false;
-    }
-
-    @Override
-    public TunnelId createTunnel(NetworkId networkId, ConnectPoint src, ConnectPoint dst) {
-        checkNotNull(networkId, NETWORK_ID_NULL);
-        checkNotNull(src, CONNECT_POINT_NULL);
-        checkNotNull(dst, CONNECT_POINT_NULL);
-        Key intentKey = encodeKey(networkId, src, dst);
-
-        List<Constraint> constraints = new ArrayList<>();
-        constraints.add(new EncapsulationConstraint(EncapsulationType.VLAN));
-
-        // TODO Currently there can only be one tunnel/intent between the src and dst across
-        // all virtual networks. We may want to support multiple intents between the same src/dst pairs.
-        PointToPointIntent intent = PointToPointIntent.builder()
-                .key(intentKey)
-                .appId(appId)
-                .ingressPoint(src)
-                .egressPoint(dst)
-                .constraints(constraints)
-                .build();
-        intentService.submit(intent);
-
-        // construct tunnelId from the key
-        return TunnelId.valueOf(intentKey.toString());
-    }
-
-    @Override
-    public void destroyTunnel(NetworkId networkId, TunnelId tunnelId) {
-        String key = tunnelId.id();
-        Key intentKey = Key.of(key, appId);
-        Intent intent = intentService.getIntent(intentKey);
-        checkNotNull(intent, INTENT_NULL);
-        intentService.withdraw(intent);
-    }
-
-    private NetworkId decodeNetworkIdFromKey(Key intentKey) {
-        // Extract the network identifier from the intent key
-        StringTokenizer tokenizer = new StringTokenizer(intentKey.toString(), ",");
-        String networkIdString = tokenizer.nextToken().substring(NETWORK_ID.length());
-        return NetworkId.networkId(Integer.valueOf(networkIdString));
-    }
-
-    private Key encodeKey(NetworkId networkId, ConnectPoint src, ConnectPoint dst) {
-        String key = String.format(KEY_FORMAT, networkId, src, dst);
-        return Key.of(key, appId);
-    }
-
-    private class InternalPtPtIntentListener implements IntentListener {
-        @Override
-        public void event(IntentEvent event) {
-            PointToPointIntent intent = (PointToPointIntent) event.subject();
-            Key intentKey = intent.key();
-
-            // Ignore intent events that are not relevant.
-            if (!isRelevant(event)) {
-                return;
-            }
-
-            NetworkId networkId = decodeNetworkIdFromKey(intentKey);
-            ConnectPoint src = intent.ingressPoint();
-            ConnectPoint dst = intent.egressPoint();
-
-            switch (event.type()) {
-                case INSTALLED:
-                    providerService.tunnelUp(networkId, src, dst, TunnelId.valueOf(intentKey.toString()));
-                    break;
-                case WITHDRAWN:
-                    intentService.purge(intent);
-                    // Fall through and notify the provider service that the tunnel is down
-                    // for both WITHDRAWN and FAILED intent event types.
-                case FAILED:
-                    providerService.tunnelDown(networkId, src, dst, TunnelId.valueOf(intentKey.toString()));
-                    break;
-                case INSTALL_REQ:
-                case CORRUPT:
-                case PURGED:
-                    break; // Not sure what do with these events, ignore for now.
-                default:
-                    break;
-            }
-        }
-
-        @Override
-        public boolean isRelevant(IntentEvent event) {
-            if (event.subject() instanceof  PointToPointIntent) {
-                PointToPointIntent intent = (PointToPointIntent) event.subject();
-
-                // Only events that are for this appId are relevent.
-                return intent.appId().equals(appId);
-            }
-            return false;
-        }
-    }
-}
-
diff --git a/incubator/net/src/test/java/org/onosproject/incubator/net/virtual/impl/PtToPtIntentVirtualNetworkProviderTest.java b/incubator/net/src/test/java/org/onosproject/incubator/net/virtual/impl/PtToPtIntentVirtualNetworkProviderTest.java
deleted file mode 100644
index dd965f8..0000000
--- a/incubator/net/src/test/java/org/onosproject/incubator/net/virtual/impl/PtToPtIntentVirtualNetworkProviderTest.java
+++ /dev/null
@@ -1,290 +0,0 @@
-/*
- * Copyright 2016-present 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.incubator.net.virtual.impl;
-
-import com.google.common.collect.Lists;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.onosproject.TestApplicationId;
-import org.onosproject.core.ApplicationId;
-import org.onosproject.core.CoreService;
-import org.onosproject.core.CoreServiceAdapter;
-import org.onosproject.core.IdGenerator;
-import org.onosproject.incubator.net.tunnel.TunnelId;
-import org.onosproject.incubator.net.virtual.NetworkId;
-import org.onosproject.incubator.net.virtual.VirtualNetworkProvider;
-import org.onosproject.incubator.net.virtual.VirtualNetworkProviderRegistry;
-import org.onosproject.incubator.net.virtual.VirtualNetworkProviderService;
-import org.onosproject.net.ConnectPoint;
-import org.onosproject.net.DeviceId;
-import org.onosproject.net.PortNumber;
-import org.onosproject.net.intent.FakeIntentManager;
-import org.onosproject.net.intent.FlowRuleIntent;
-import org.onosproject.net.intent.Intent;
-import org.onosproject.net.intent.IntentCompiler;
-import org.onosproject.net.intent.IntentEvent;
-import org.onosproject.net.intent.IntentExtensionService;
-import org.onosproject.net.intent.IntentListener;
-import org.onosproject.net.intent.IntentTestsMocks;
-import org.onosproject.net.intent.MockIdGenerator;
-import org.onosproject.net.intent.PointToPointIntent;
-import org.onosproject.net.intent.TestableIntentService;
-import org.onosproject.net.provider.AbstractProviderService;
-import org.onosproject.net.provider.ProviderId;
-
-import java.util.Collections;
-import java.util.List;
-import java.util.Set;
-import java.util.concurrent.Semaphore;
-import java.util.concurrent.TimeUnit;
-import java.util.concurrent.atomic.AtomicLong;
-
-import static org.easymock.EasyMock.*;
-import static org.junit.Assert.*;
-
-/**
- * Junit tests for PtToPtIntentVirtualNetworkProvider.
- */
-public class PtToPtIntentVirtualNetworkProviderTest {
-
-    private PtToPtIntentVirtualNetworkProvider provider;
-    private VirtualNetworkProviderRegistry providerRegistry;
-
-    private final VirtualNetworkRegistryAdapter virtualNetworkRegistry = new VirtualNetworkRegistryAdapter();
-    private TestableIntentService intentService = new FakeIntentManager();
-    private TestListener listener = new TestListener();
-    protected TestIntentCompiler compiler = new TestIntentCompiler();
-    private IntentExtensionService intentExtensionService;
-
-    private static final ApplicationId APP_ID =
-            TestApplicationId.create(PtToPtIntentVirtualNetworkProvider.PTPT_INTENT_APPID);
-
-    private IdGenerator idGenerator = new MockIdGenerator();
-    private static final int MAX_WAIT_TIME = 5;
-    private static final int MAX_PERMITS = 2;
-    private static Semaphore created;
-    private static Semaphore removed;
-
-    @Before
-    public void setUp() {
-        provider = new PtToPtIntentVirtualNetworkProvider();
-        provider.providerRegistry = virtualNetworkRegistry;
-        final CoreService mockCoreService = createMock(CoreService.class);
-        provider.coreService = mockCoreService;
-        expect(mockCoreService.registerApplication(PtToPtIntentVirtualNetworkProvider.PTPT_INTENT_APPID))
-                .andReturn(APP_ID).anyTimes();
-        replay(mockCoreService);
-        Intent.unbindIdGenerator(idGenerator);
-        Intent.bindIdGenerator(idGenerator);
-
-        intentService.addListener(listener);
-        provider.intentService = intentService;
-
-        // Register a compiler and an installer both setup for success.
-        intentExtensionService = intentService;
-        intentExtensionService.registerCompiler(PointToPointIntent.class, compiler);
-
-        provider.activate();
-        created = new Semaphore(0, true);
-        removed = new Semaphore(0, true);
-    }
-
-    @After
-    public void tearDown() {
-        Intent.unbindIdGenerator(idGenerator);
-        intentService.removeListener(listener);
-        provider.deactivate();
-        provider.providerRegistry = null;
-        provider.coreService = null;
-        provider.intentService = null;
-        created = null;
-        removed = null;
-    }
-
-    @Test
-    public void basics() {
-        assertNotNull("registration expected", provider);
-    }
-
-    /**
-     * Test a null network identifier.
-     */
-    @Test(expected = NullPointerException.class)
-    public void testCreateTunnelNullNetworkId() {
-        provider.createTunnel(null, null, null);
-    }
-
-    /**
-     * Test a null source connect point.
-     */
-    @Test(expected = NullPointerException.class)
-    public void testCreateTunnelNullSrc() {
-        ConnectPoint dst = new ConnectPoint(DeviceId.deviceId("device2"), PortNumber.portNumber(2));
-
-        provider.createTunnel(NetworkId.networkId(0), null, dst);
-    }
-
-    /**
-     * Test a null destination connect point.
-     */
-    @Test(expected = NullPointerException.class)
-    public void testCreateTunnelNullDst() {
-        ConnectPoint src = new ConnectPoint(DeviceId.deviceId("device1"), PortNumber.portNumber(1));
-
-        provider.createTunnel(NetworkId.networkId(0), src, null);
-    }
-
-    /**
-     * Test creating/destroying a valid tunnel.
-     */
-    @Test
-    public void testCreateRemoveTunnel() {
-        NetworkId networkId = NetworkId.networkId(0);
-        ConnectPoint src = new ConnectPoint(DeviceId.deviceId("device1"), PortNumber.portNumber(1));
-        ConnectPoint dst = new ConnectPoint(DeviceId.deviceId("device2"), PortNumber.portNumber(2));
-
-        TunnelId tunnelId = provider.createTunnel(networkId, src, dst);
-
-        // Wait for the tunnel to go into an INSTALLED state, and that the tunnelUp method was called.
-        try {
-            if (!created.tryAcquire(MAX_PERMITS, MAX_WAIT_TIME, TimeUnit.SECONDS)) {
-                fail("Failed to wait for tunnel to get installed.");
-            }
-        } catch (InterruptedException e) {
-            fail("Semaphore exception during tunnel installation." + e.getMessage());
-        }
-
-        String key = String.format(PtToPtIntentVirtualNetworkProvider.KEY_FORMAT,
-                                   networkId.toString(), src.toString(), dst.toString());
-
-        assertEquals("TunnelId does not match as expected.", key, tunnelId.toString());
-        provider.destroyTunnel(networkId, tunnelId);
-
-        // Wait for the tunnel to go into a WITHDRAWN state, and that the tunnelDown method was called.
-        try {
-            if (!removed.tryAcquire(MAX_PERMITS, MAX_WAIT_TIME, TimeUnit.SECONDS)) {
-                fail("Failed to wait for tunnel to get removed.");
-            }
-        } catch (InterruptedException e) {
-            fail("Semaphore exception during tunnel removal." + e.getMessage());
-        }
-    }
-
-    /**
-     * Virtual network registry implementation for this test class.
-     */
-    private class VirtualNetworkRegistryAdapter implements VirtualNetworkProviderRegistry {
-        private VirtualNetworkProvider provider;
-
-        @Override
-        public VirtualNetworkProviderService register(VirtualNetworkProvider theProvider) {
-            this.provider = theProvider;
-            return new TestVirtualNetworkProviderService(theProvider);
-        }
-
-        @Override
-        public void unregister(VirtualNetworkProvider theProvider) {
-            this.provider = null;
-        }
-
-        @Override
-        public Set<ProviderId> getProviders() {
-            return null;
-        }
-    }
-
-    /**
-     * Virtual network provider service implementation for this test class.
-     */
-    private class TestVirtualNetworkProviderService
-            extends AbstractProviderService<VirtualNetworkProvider>
-            implements VirtualNetworkProviderService {
-
-        protected TestVirtualNetworkProviderService(VirtualNetworkProvider provider) {
-            super(provider);
-        }
-
-        @Override
-        public void topologyChanged(Set<Set<ConnectPoint>> clusters) {
-
-        }
-
-        @Override
-        public void tunnelUp(NetworkId networkId, ConnectPoint src, ConnectPoint dst, TunnelId tunnelId) {
-            // Release one permit on the created semaphore since the tunnelUp method was called.
-            created.release();
-        }
-
-        @Override
-        public void tunnelDown(NetworkId networkId, ConnectPoint src, ConnectPoint dst, TunnelId tunnelId) {
-            // Release one permit on the removed semaphore since the tunnelDown method was called.
-            removed.release();
-        }
-    }
-
-    private static class TestListener implements IntentListener {
-
-        @Override
-        public void event(IntentEvent event) {
-            switch (event.type()) {
-                case INSTALLED:
-                    // Release one permit on the created semaphore since the Intent event was received.
-                    created.release();
-                    break;
-                case WITHDRAWN:
-                    // Release one permit on the removed semaphore since the Intent event was received.
-                    removed.release();
-                    break;
-                default:
-                    break;
-            }
-        }
-    }
-
-    /**
-     * Core service test class.
-     */
-    private class TestCoreService extends CoreServiceAdapter {
-
-        @Override
-        public IdGenerator getIdGenerator(String topic) {
-            return new IdGenerator() {
-                private AtomicLong counter = new AtomicLong(0);
-
-                @Override
-                public long getNewId() {
-                    return counter.getAndIncrement();
-                }
-            };
-        }
-    }
-
-    private static class TestIntentCompiler implements IntentCompiler<PointToPointIntent> {
-        @Override
-        public List<Intent> compile(PointToPointIntent intent, List<Intent> installable) {
-            return Lists.newArrayList(new MockInstallableIntent());
-        }
-    }
-
-    private static class MockInstallableIntent extends FlowRuleIntent {
-
-        public MockInstallableIntent() {
-            super(APP_ID, Collections.singletonList(new IntentTestsMocks.MockFlowRule(100)), Collections.emptyList());
-        }
-    }
-}
diff --git a/incubator/net/src/test/java/org/onosproject/incubator/net/virtual/impl/VirtualNetworkIntentServiceTest.java b/incubator/net/src/test/java/org/onosproject/incubator/net/virtual/impl/VirtualNetworkIntentServiceTest.java
index ef8de45..5e2d06c 100644
--- a/incubator/net/src/test/java/org/onosproject/incubator/net/virtual/impl/VirtualNetworkIntentServiceTest.java
+++ b/incubator/net/src/test/java/org/onosproject/incubator/net/virtual/impl/VirtualNetworkIntentServiceTest.java
@@ -81,7 +81,7 @@
 
     private final String tenantIdValue1 = "TENANT_ID1";
     private static final ApplicationId APP_ID =
-            new TestApplicationId(PtToPtIntentVirtualNetworkProvider.PTPT_INTENT_APPID);
+            new TestApplicationId("MyAppId");
 
     private ConnectPoint cp1;
     private ConnectPoint cp2;
