diff --git a/apps/cfm/src/main/java/org/onosproject/cfm/impl/CfmWebApplication.java b/apps/cfm/src/main/java/org/onosproject/cfm/impl/CfmWebApplication.java
new file mode 100644
index 0000000..f21b66d
--- /dev/null
+++ b/apps/cfm/src/main/java/org/onosproject/cfm/impl/CfmWebApplication.java
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2017-present Open Networking Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.onosproject.cfm.impl;
+
+import java.util.Set;
+
+import org.onlab.rest.AbstractWebApplication;
+import org.onosproject.soam.impl.DmWebResource;
+import org.onosproject.soam.impl.LmWebResource;
+
+/**
+ * CFM REST API web application.
+ */
+public class CfmWebApplication extends AbstractWebApplication {
+    @Override
+    public Set<Class<?>> getClasses() {
+        return getClasses(
+                MdWebResource.class,
+                MaWebResource.class,
+                MepWebResource.class,
+                DmWebResource.class,
+                LmWebResource.class);
+    }
+}
diff --git a/apps/cfm/src/main/java/org/onosproject/cfm/impl/MaWebResource.java b/apps/cfm/src/main/java/org/onosproject/cfm/impl/MaWebResource.java
new file mode 100644
index 0000000..c861314
--- /dev/null
+++ b/apps/cfm/src/main/java/org/onosproject/cfm/impl/MaWebResource.java
@@ -0,0 +1,177 @@
+/*
+ * Copyright 2017-present Open Networking Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onosproject.cfm.impl;
+
+import java.io.InputStream;
+import java.net.URI;
+
+import javax.ws.rs.Consumes;
+import javax.ws.rs.DELETE;
+import javax.ws.rs.GET;
+import javax.ws.rs.POST;
+import javax.ws.rs.Path;
+import javax.ws.rs.PathParam;
+import javax.ws.rs.Produces;
+import javax.ws.rs.core.MediaType;
+import javax.ws.rs.core.Response;
+
+import org.onosproject.cfm.web.MaintenanceAssociationCodec;
+import org.onosproject.codec.JsonCodec;
+import org.onosproject.incubator.net.l2monitoring.cfm.MaintenanceAssociation;
+import org.onosproject.incubator.net.l2monitoring.cfm.MaintenanceDomain;
+import org.onosproject.incubator.net.l2monitoring.cfm.identifier.MaIdCharStr;
+import org.onosproject.incubator.net.l2monitoring.cfm.identifier.MaIdShort;
+import org.onosproject.incubator.net.l2monitoring.cfm.identifier.MdId;
+import org.onosproject.incubator.net.l2monitoring.cfm.identifier.MdIdCharStr;
+import org.onosproject.incubator.net.l2monitoring.cfm.service.CfmConfigException;
+import org.onosproject.incubator.net.l2monitoring.cfm.service.CfmMdService;
+import org.onosproject.rest.AbstractWebResource;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.fasterxml.jackson.databind.JsonNode;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import com.fasterxml.jackson.databind.node.ObjectNode;
+
+/**
+ * Layer 2 CFM Maintenance Association web resource.
+ */
+@Path("md/{md_name}/ma")
+public class MaWebResource extends AbstractWebResource {
+    private final Logger log = LoggerFactory.getLogger(getClass());
+
+    /**
+     * Get Maintenance Association by MD and MA name.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @param maName The name of a Maintenance Association belonging to the MD
+     * @return 200 OK with details of MA or 500 on Error
+     */
+    @GET
+    @Path("{ma_name}")
+    @Produces(MediaType.APPLICATION_JSON)
+    @Consumes(MediaType.APPLICATION_JSON)
+    public Response getMa(@PathParam("md_name") String mdName,
+                          @PathParam("ma_name") String maName) {
+        log.debug("GET called for MA {}/{}", mdName, maName);
+        try {
+            MdId mdId = MdIdCharStr.asMdId(mdName);
+            MaIdShort maId = MaIdCharStr.asMaId(maName);
+            MaintenanceAssociation ma = get(CfmMdService.class)
+                .getMaintenanceAssociation(mdId, maId)
+                .orElseThrow(() -> new IllegalArgumentException(
+                        "MA " + maName + " not Found"));
+            ObjectNode node = mapper().createObjectNode();
+            node.set("ma", codec(MaintenanceAssociation.class).encode(ma, this));
+            return ok(node).build();
+        } catch (IllegalArgumentException e) {
+            log.error("Get MA {} failed", mdName + "/" + maName, e);
+            return Response.serverError()
+                    .entity("{ \"failure\":\"" + e.toString() + "\" }").build();
+        }
+    }
+
+    /**
+     * Delete the Maintenance Association by MD and MA name.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @param maName The name of a Maintenance Association belonging to the MD
+     * @return 200 OK if removed, 304 if item was not found or 500 on Error
+     */
+    @DELETE
+    @Path("{ma_name}")
+    @Consumes(MediaType.APPLICATION_JSON)
+    @Produces(MediaType.APPLICATION_JSON)
+    public Response deleteMa(@PathParam("md_name") String mdName,
+                             @PathParam("ma_name") String maName) {
+        log.debug("DELETE called for MA {}/{}", mdName, maName);
+        try {
+            MdId mdId = MdIdCharStr.asMdId(mdName);
+            MaIdShort maId = MaIdCharStr.asMaId(maName);
+            boolean deleted = get(CfmMdService.class)
+                                        .deleteMaintenanceAssociation(mdId, maId);
+            if (!deleted) {
+                return Response.notModified(mdName + "/"
+                                            + maName + " did not exist").build();
+            } else {
+                return ok("{ \"success\":\"deleted " + mdName
+                                                + "/" + maName + "\" }").build();
+            }
+        } catch (CfmConfigException e) {
+            log.error("Delete Maintenance Association {} failed",
+                    mdName + "/" + maName, e);
+            return Response.serverError().entity("{ \"failure\":\"" +
+                                                e.toString() + "\" }").build();
+        }
+    }
+
+    /**
+     * Create Maintenance Association by MD and MA name.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @param input A JSON formatted input stream specifying the MA parameters
+     * @return 200 OK or 500 on error
+     */
+    @POST
+    @Consumes(MediaType.APPLICATION_JSON)
+    @Produces(MediaType.APPLICATION_JSON)
+    public Response createMaintenanceAssociation(@PathParam("md_name") String mdName,
+                                                 InputStream input) {
+        log.debug("POST called to Create MA");
+        try {
+            MdId mdId = MdIdCharStr.asMdId(mdName);
+            MaintenanceDomain md = get(CfmMdService.class)
+                                            .getMaintenanceDomain(mdId).get();
+            if (md == null) {
+                return Response.serverError().entity("{ \"failure\":\"md "
+                                        + mdName + " does not exist\" }").build();
+            }
+
+            ObjectMapper mapper = new ObjectMapper();
+            JsonNode cfg = mapper.readTree(input);
+            JsonCodec<MaintenanceAssociation> maCodec =
+                                            codec(MaintenanceAssociation.class);
+
+            MaintenanceAssociation ma;
+            try {
+                ma = ((MaintenanceAssociationCodec) maCodec)
+                        .decode((ObjectNode) cfg, this, mdId.getNameLength());
+            } catch (Exception e) {
+                log.error("Create MaintenanceAssociation on MD {} failed", mdName, e);
+                return Response.serverError()
+                        .entity("{ \"failure\":\"" + e.toString() + "\" }")
+                        .build();
+            }
+
+            Boolean alreadyExists = get(CfmMdService.class)
+                                        .createMaintenanceAssociation(mdId, ma);
+            if (alreadyExists) {
+                return Response.notModified(mdName + "/" + ma.maId() +
+                                                    " already exists").build();
+            }
+            return Response
+                    .created(new URI("md/" + mdName + "/ma/" + ma.maId()))
+                    .entity("{ \"success\":\"" + mdName + "/" + ma.maId() + " created\" }")
+                    .build();
+
+        } catch (Exception | CfmConfigException e) {
+            log.error("Create MaintenanceAssociation on MD {} failed", mdName, e);
+            return Response.serverError()
+                    .entity("{ \"failure\":\"" + e.toString() + "\" }")
+                    .build();
+        }
+    }
+}
diff --git a/apps/cfm/src/main/java/org/onosproject/cfm/impl/MdWebResource.java b/apps/cfm/src/main/java/org/onosproject/cfm/impl/MdWebResource.java
new file mode 100644
index 0000000..ecf1fe9
--- /dev/null
+++ b/apps/cfm/src/main/java/org/onosproject/cfm/impl/MdWebResource.java
@@ -0,0 +1,156 @@
+/*
+ * Copyright 2017-present Open Networking Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onosproject.cfm.impl;
+
+import java.io.InputStream;
+import java.net.URI;
+import java.util.Collection;
+
+import javax.ws.rs.Consumes;
+import javax.ws.rs.DELETE;
+import javax.ws.rs.GET;
+import javax.ws.rs.POST;
+import javax.ws.rs.Path;
+import javax.ws.rs.PathParam;
+import javax.ws.rs.Produces;
+import javax.ws.rs.core.MediaType;
+import javax.ws.rs.core.Response;
+
+import org.onosproject.incubator.net.l2monitoring.cfm.MaintenanceDomain;
+import org.onosproject.incubator.net.l2monitoring.cfm.identifier.MdId;
+import org.onosproject.incubator.net.l2monitoring.cfm.identifier.MdIdCharStr;
+import org.onosproject.incubator.net.l2monitoring.cfm.service.CfmConfigException;
+import org.onosproject.incubator.net.l2monitoring.cfm.service.CfmMdService;
+import org.onosproject.rest.AbstractWebResource;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.fasterxml.jackson.databind.JsonNode;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import com.fasterxml.jackson.databind.node.ArrayNode;
+import com.fasterxml.jackson.databind.node.ObjectNode;
+
+/**
+ * Layer 2 CFM Maintenance Domain web resource.
+ */
+@Path("md")
+public class MdWebResource extends AbstractWebResource {
+    private final Logger log = LoggerFactory.getLogger(getClass());
+    public static final String JSON_NOT_NULL = "JsonNode can not be null";
+
+    /**
+     * Get all Maintenance Domains.
+     *
+     * @return 200 OK with a list of MDs and their children
+     */
+    @GET
+    @Produces(MediaType.APPLICATION_JSON)
+    @Consumes(MediaType.APPLICATION_JSON)
+    public Response getMds() {
+        log.debug("GET called for all MDs");
+        Collection<MaintenanceDomain> mdMap =
+                                get(CfmMdService.class).getAllMaintenanceDomain();
+        ArrayNode arrayNode = mapper().createArrayNode();
+        arrayNode.add(codec(MaintenanceDomain.class).encode(mdMap, this));
+        return ok(mapper().createObjectNode().set("mds", arrayNode)).build();
+    }
+
+    /**
+     * Get Maintenance Domain by name.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @return 200 OK with the details of the MD and its children or 500 on error
+     */
+    @GET
+    @Path("{md_name}")
+    @Produces(MediaType.APPLICATION_JSON)
+    @Consumes(MediaType.APPLICATION_JSON)
+    public Response getMd(@PathParam("md_name") String mdName) {
+        log.debug("GET called for MD {}", mdName);
+        try {
+            MaintenanceDomain md = get(CfmMdService.class)
+                    .getMaintenanceDomain(MdIdCharStr.asMdId(mdName))
+                    .orElseThrow(() -> new IllegalArgumentException(
+                            "MD " + mdName + " not Found"));
+            ObjectNode result = mapper().createObjectNode();
+            result.set("md", codec(MaintenanceDomain.class).encode(md, this));
+            return ok(result.toString()).build();
+        } catch (IllegalArgumentException e) {
+            log.error("Get MD {} failed", mdName, e);
+            return Response.serverError()
+                    .entity("{ \"failure\":\"" + e.toString() + "\" }").build();
+        }
+    }
+
+    /**
+     * Delete Maintenance Domain by name.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @return 200 OK, or 304 if not found or 500 on error
+     */
+    @DELETE
+    @Path("{md_name}")
+    @Consumes(MediaType.APPLICATION_JSON)
+    @Produces(MediaType.APPLICATION_JSON)
+    public Response deleteMd(@PathParam("md_name") String mdName) {
+        log.debug("DELETE called for MD {}", mdName);
+        try {
+            MdId mdId = MdIdCharStr.asMdId(mdName);
+            boolean deleted = get(CfmMdService.class).deleteMaintenanceDomain(mdId);
+            if (!deleted) {
+                return Response.notModified(mdName + " did not exist").build();
+            } else {
+                return ok("{ \"success\":\"deleted " + mdName + "\" }").build();
+            }
+        } catch (CfmConfigException e) {
+            log.error("Delete Maintenance Domain {} failed", mdName, e);
+            return Response.serverError()
+                    .entity("{ \"failure\":\"" + e.toString() + "\" }").build();
+        }
+    }
+
+    /**
+     * Create Maintenance Domain.
+     *
+     * @param input A JSON formatted input stream specifying the MA parameters
+     * @return 200 OK, 304 if MD already exists or 500 on error
+     */
+    @POST
+    @Consumes(MediaType.APPLICATION_JSON)
+    @Produces(MediaType.APPLICATION_JSON)
+    public Response createMaintenanceDomain(InputStream input) {
+        log.debug("POST called to Create MD");
+        try {
+            ObjectMapper mapper = new ObjectMapper();
+            JsonNode cfg = mapper.readTree(input);
+            MaintenanceDomain md = codec(MaintenanceDomain.class).decode((ObjectNode) cfg, this);
+
+            if (get(CfmMdService.class).createMaintenanceDomain(md)) {
+                return Response.notModified(md.mdId().toString() + " already exists").build();
+            }
+            return Response
+                    .created(new URI("md/" + md.mdId()))
+                    .entity("{ \"success\":\"" + md.mdId() + " created\" }")
+                    .build();
+
+        } catch (Exception | CfmConfigException e) {
+            log.error("Create MaintenanceDomain", e);
+            return Response.serverError()
+                    .entity("{ \"failure\":\"" + e.toString() + "\" }")
+                    .build();
+        }
+    }
+}
diff --git a/apps/cfm/src/main/java/org/onosproject/cfm/impl/MepWebResource.java b/apps/cfm/src/main/java/org/onosproject/cfm/impl/MepWebResource.java
new file mode 100644
index 0000000..2486df0
--- /dev/null
+++ b/apps/cfm/src/main/java/org/onosproject/cfm/impl/MepWebResource.java
@@ -0,0 +1,343 @@
+/*
+ * Copyright 2017-present Open Networking Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.onosproject.cfm.impl;
+
+import java.io.InputStream;
+import java.net.URI;
+import java.util.Collection;
+
+import javax.ws.rs.Consumes;
+import javax.ws.rs.DELETE;
+import javax.ws.rs.GET;
+import javax.ws.rs.POST;
+import javax.ws.rs.PUT;
+import javax.ws.rs.Path;
+import javax.ws.rs.PathParam;
+import javax.ws.rs.Produces;
+import javax.ws.rs.core.MediaType;
+import javax.ws.rs.core.Response;
+
+import org.onosproject.cfm.web.MepCodec;
+import org.onosproject.codec.JsonCodec;
+import org.onosproject.incubator.net.l2monitoring.cfm.MaintenanceAssociation;
+import org.onosproject.incubator.net.l2monitoring.cfm.MaintenanceDomain;
+import org.onosproject.incubator.net.l2monitoring.cfm.Mep;
+import org.onosproject.incubator.net.l2monitoring.cfm.MepEntry;
+import org.onosproject.incubator.net.l2monitoring.cfm.MepLbCreate;
+import org.onosproject.incubator.net.l2monitoring.cfm.MepLtCreate;
+import org.onosproject.incubator.net.l2monitoring.cfm.identifier.MaIdCharStr;
+import org.onosproject.incubator.net.l2monitoring.cfm.identifier.MaIdShort;
+import org.onosproject.incubator.net.l2monitoring.cfm.identifier.MdId;
+import org.onosproject.incubator.net.l2monitoring.cfm.identifier.MdIdCharStr;
+import org.onosproject.incubator.net.l2monitoring.cfm.identifier.MepId;
+import org.onosproject.incubator.net.l2monitoring.cfm.service.CfmConfigException;
+import org.onosproject.incubator.net.l2monitoring.cfm.service.CfmMdService;
+import org.onosproject.incubator.net.l2monitoring.cfm.service.CfmMepService;
+import org.onosproject.rest.AbstractWebResource;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.fasterxml.jackson.databind.JsonNode;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import com.fasterxml.jackson.databind.node.ArrayNode;
+import com.fasterxml.jackson.databind.node.ObjectNode;
+
+/**
+ * Layer 2 CFM Maintenance Association Endpoint (MEP) web resource.
+ */
+@Path("md/{md_name}/ma/{ma_name}/mep")
+public class MepWebResource extends AbstractWebResource {
+    private final Logger log = LoggerFactory.getLogger(getClass());
+
+    /**
+     * Get all MEPs by MD name, MA name.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @param maName The name of a Maintenance Association belonging to the MD
+     * @return 200 OK with a list of MEPS or 500 on error
+     */
+    @GET
+    @Produces(MediaType.APPLICATION_JSON)
+    @Consumes(MediaType.APPLICATION_JSON)
+    public Response getAllMepsForMa(@PathParam("md_name") String mdName,
+            @PathParam("ma_name") String maName) {
+        log.debug("GET all Meps called for MA {}", mdName + "/" + maName);
+        try {
+            MdId mdId = MdIdCharStr.asMdId(mdName);
+            MaIdShort maId = MaIdCharStr.asMaId(maName);
+            Collection<MepEntry> mepCollection = get(CfmMepService.class).getAllMeps(mdId, maId);
+            ArrayNode an = mapper().createArrayNode();
+            an.add(codec(MepEntry.class).encode(mepCollection, this));
+            return ok(mapper().createObjectNode().set("meps", an)).build();
+        } catch (CfmConfigException e) {
+            log.error("Get all Meps on {} failed because of exception",
+                    mdName + "/" + maName, e);
+            return Response.serverError().entity("{ \"failure\":\"" + e.toString() + "\" }").build();
+        }
+
+    }
+
+    /**
+     * Get MEP by MD name, MA name and Mep Id.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @param maName The name of a Maintenance Association belonging to the MD
+     * @param mepId The Id of the MEP
+     * @return 200 OK with details of the MEP or 500 on error
+     */
+    @GET
+    @Path("{mep_id}")
+    @Produces(MediaType.APPLICATION_JSON)
+    @Consumes(MediaType.APPLICATION_JSON)
+    public Response getMep(@PathParam("md_name") String mdName,
+            @PathParam("ma_name") String maName,
+            @PathParam("mep_id") short mepId) {
+        log.debug("GET called for MEP {}", mdName + "/" + maName + "/" + mepId);
+        try {
+            MdId mdId = MdIdCharStr.asMdId(mdName);
+            MaIdShort maId = MaIdCharStr.asMaId(maName);
+            MepEntry mepEntry = get(CfmMepService.class)
+                    .getMep(mdId, maId, MepId.valueOf(mepId));
+            if (mepEntry == null) {
+                return Response.serverError().entity("{ \"failure\":\"MEP " +
+                        mdName + "/" + maName + "/" + mepId + " not found\" }").build();
+            }
+            ObjectNode node = mapper().createObjectNode();
+            node.set("mep", codec(MepEntry.class).encode(mepEntry, this));
+            return ok(node).build();
+        } catch (CfmConfigException e) {
+            log.error("Get Mep {} failed because of exception",
+                    mdName + "/" + maName + "/" + mepId, e);
+            return Response.serverError().entity("{ \"failure\":\"" + e.toString() + "\" }").build();
+        }
+    }
+
+    /**
+     * Delete MEP by MD name, MA name and Mep Id.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @param maName The name of a Maintenance Association belonging to the MD
+     * @param mepIdShort The Id of the MEP
+     * @return 200 OK or 304 if not found, or 500 on error
+     */
+    @DELETE
+    @Path("{mep_id}")
+    @Consumes(MediaType.APPLICATION_JSON)
+    @Produces(MediaType.APPLICATION_JSON)
+    public Response deleteMep(@PathParam("md_name") String mdName,
+            @PathParam("ma_name") String maName,
+            @PathParam("mep_id") short mepIdShort) {
+        log.debug("DELETE called for MEP " + mdName + "/" + maName + "/" + mepIdShort);
+        try {
+            MdId mdId = MdIdCharStr.asMdId(mdName);
+            MaIdShort maId = MaIdCharStr.asMaId(maName);
+            boolean deleted = get(CfmMepService.class)
+                    .deleteMep(mdId, maId, MepId.valueOf(mepIdShort));
+            if (!deleted) {
+                return Response.notModified(mdName + "/" + maName + "/" +
+                        mepIdShort + " did not exist").build();
+            } else {
+                return ok("{ \"success\":\"deleted " + mdName + "/" + maName +
+                        "/" + mepIdShort + "\" }").build();
+            }
+        } catch (CfmConfigException e) {
+            log.error("Delete Mep {} failed because of exception ",
+                    mdName + "/" + maName + "/" + mepIdShort, e);
+            return Response.serverError().entity("{ \"failure\":\"" +
+                    e.toString() + "\" }").build();
+        }
+    }
+
+    /**
+     * Create MEP with MD name, MA name and Mep Json.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @param maName The name of a Maintenance Association belonging to the MD
+     * @param input A JSON formatted input stream specifying the Mep parameters
+     * @return 201 Created or 304 if already exists or 500 on error
+     */
+    @POST
+    @Consumes(MediaType.APPLICATION_JSON)
+    @Produces(MediaType.APPLICATION_JSON)
+    public Response createMep(@PathParam("md_name") String mdName,
+                              @PathParam("ma_name") String maName, InputStream input) {
+        log.debug("POST called to Create Mep");
+        try {
+            MdId mdId = MdIdCharStr.asMdId(mdName);
+            MaIdShort maId = MaIdCharStr.asMaId(maName);
+            MaintenanceAssociation ma = get(CfmMdService.class).getMaintenanceAssociation(mdId, maId).get();
+
+            ObjectMapper mapper = new ObjectMapper();
+            JsonNode cfg = mapper.readTree(input);
+            JsonCodec<Mep> mepCodec = codec(Mep.class);
+
+            Mep mep = ((MepCodec) mepCodec).decode((ObjectNode) cfg, this, mdName, maName);
+
+            Boolean issuccess = get(CfmMepService.class).createMep(mdId, maId, mep);
+            if (!issuccess) {
+                return Response.notModified(mdName + "/" + ma.maId() + "/" + mep.mepId() +
+                        " already exists").build();
+            }
+            return Response
+                    .created(new URI("md/" + mdName + "/ma/" + ma.maId() + "/mep/" + mep.mepId()))
+                    .entity("{ \"success\":\"mep " + mdName + "/" + ma.maId() + "/" + mep.mepId() + " created\" }")
+                    .build();
+        } catch (Exception | CfmConfigException e) {
+            log.error("Create Mep on " + mdName + "/" + maName + " failed because of exception {}",
+                      e.toString());
+            return Response.serverError()
+                    .entity("{ \"failure\":\"" + e.toString() + "\" }")
+                    .build();
+        }
+    }
+
+    /**
+     * Transmit Loopback on MEP with MD name, MA name and Mep Id.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @param maName The name of a Maintenance Association belonging to the MD
+     * @param mepIdShort The id of a MEP belonging to the MA
+     * @param input A JSON formatted input stream specifying the Mep parameters
+     * @return 202 Received with success message or 500 on error
+     */
+    @PUT
+    @Path("{mep_id}/transmit-loopback")
+    @Consumes(MediaType.APPLICATION_JSON)
+    @Produces(MediaType.APPLICATION_JSON)
+    public Response transmitLoopback(
+            @PathParam("md_name") String mdName,
+            @PathParam("ma_name") String maName,
+            @PathParam("mep_id") short mepIdShort,
+            InputStream input) {
+        log.debug("PUT called to Transmit Loopback on Mep");
+
+        MdId mdId = MdIdCharStr.asMdId(mdName);
+        MaIdShort maId = MaIdCharStr.asMaId(maName);
+        MaintenanceDomain md = get(CfmMdService.class).getMaintenanceDomain(mdId).get();
+        MaintenanceAssociation ma = get(CfmMdService.class)
+                .getMaintenanceAssociation(mdId, maId).get();
+
+        MepId mepId = MepId.valueOf(mepIdShort);
+
+        try {
+            ObjectMapper mapper = new ObjectMapper();
+            JsonNode cfg = mapper.readTree(input);
+            JsonCodec<MepLbCreate> mepLbCreateCodec = codec(MepLbCreate.class);
+
+            MepLbCreate lbCreate = mepLbCreateCodec.decode((ObjectNode) cfg, this);
+            get(CfmMepService.class).transmitLoopback(md.mdId(), ma.maId(), mepId, lbCreate);
+        } catch (Exception | CfmConfigException e) {
+            log.error("Transmit Loopback on " + mdName + "/" + maName +
+                    "/{} failed", String.valueOf(mepIdShort), e);
+            return Response.serverError()
+                  .entity("{ \"failure\":\"" + e.toString() + "\" }")
+                  .build();
+        }
+
+        return Response.accepted()
+            .entity("{ \"success\":\"Loopback on MEP " + mdName + "/" + ma.maId() + "/"
+                    + mepId.id() + " started\" }").build();
+    }
+
+    /**
+     * Abort Loopback on MEP with MD name, MA name and Mep Id.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @param maName The name of a Maintenance Association belonging to the MD
+     * @param mepIdShort The id of a MEP belonging to the MA
+     * @return 202 Received with success message or 500 on error
+     */
+    @PUT
+    @Path("{mep_id}/abort-loopback")
+    @Consumes(MediaType.APPLICATION_JSON)
+    @Produces(MediaType.APPLICATION_JSON)
+    public Response abortLoopback(
+            @PathParam("md_name") String mdName,
+            @PathParam("ma_name") String maName,
+            @PathParam("mep_id") short mepIdShort) {
+        log.debug("PUT called to Abort Loopback on Mep");
+
+        MdId mdId = MdIdCharStr.asMdId(mdName);
+        MaIdShort maId = MaIdCharStr.asMaId(maName);
+        MaintenanceDomain md = get(CfmMdService.class).getMaintenanceDomain(mdId).get();
+        MaintenanceAssociation ma = get(CfmMdService.class)
+                .getMaintenanceAssociation(mdId, maId).get();
+
+        MepId mepId = MepId.valueOf(mepIdShort);
+
+        try {
+            get(CfmMepService.class).abortLoopback(md.mdId(), ma.maId(), mepId);
+        } catch (CfmConfigException e) {
+            log.error("Abort Loopback on " + mdName + "/" + maName +
+                    "/{} failed", String.valueOf(mepIdShort), e);
+            return Response.serverError()
+                  .entity("{ \"failure\":\"" + e.toString() + "\" }")
+                  .build();
+        }
+
+        return Response.accepted()
+            .entity("{ \"success\":\"Loopback on MEP " + mdName + "/" + ma.maId() + "/"
+                    + mepId.id() + " aborted\" }").build();
+    }
+
+    /**
+     * Transmit Linktrace on MEP with MD name, MA name and Mep Id.
+     *
+     * @param mdName The name of a Maintenance Domain
+     * @param maName The name of a Maintenance Association belonging to the MD
+     * @param mepIdShort The id of a MEP belonging to the MA
+     * @param input A JSON formatted input stream specifying the Linktrace parameters
+     * @return 202 Received with success message or 500 on error
+     */
+    @PUT
+    @Path("{mep_id}/transmit-linktrace")
+    @Consumes(MediaType.APPLICATION_JSON)
+    @Produces(MediaType.APPLICATION_JSON)
+    public Response transmitLinktrace(
+            @PathParam("md_name") String mdName,
+            @PathParam("ma_name") String maName,
+            @PathParam("mep_id") short mepIdShort,
+            InputStream input) {
+        log.debug("PUT called to Transmit Linktrace on Mep");
+
+        MdId mdId = MdIdCharStr.asMdId(mdName);
+        MaIdShort maId = MaIdCharStr.asMaId(maName);
+        MaintenanceDomain md = get(CfmMdService.class).getMaintenanceDomain(mdId).get();
+        MaintenanceAssociation ma = get(CfmMdService.class)
+                .getMaintenanceAssociation(mdId, maId).get();
+
+        MepId mepId = MepId.valueOf(mepIdShort);
+
+        try {
+            ObjectMapper mapper = new ObjectMapper();
+            JsonNode cfg = mapper.readTree(input);
+            JsonCodec<MepLtCreate> mepLtCreateCodec = codec(MepLtCreate.class);
+
+            MepLtCreate ltCreate = mepLtCreateCodec.decode((ObjectNode) cfg, this);
+            get(CfmMepService.class).transmitLinktrace(md.mdId(), ma.maId(), mepId, ltCreate);
+        } catch (Exception | CfmConfigException e) {
+            log.error("Transmit Linktrace on " + mdName + "/" + maName +
+                    "/{} failed", String.valueOf(mepIdShort), e);
+            return Response.serverError()
+                    .entity("{ \"failure\":\"" + e.toString() + "\" }")
+                    .build();
+        }
+
+        return Response.accepted()
+                .entity("{ \"success\":\"Linktrace on MEP " + mdName + "/" + ma.maId() + "/"
+                        + mepId.id() + " started\" }").build();
+    }
+}
diff --git a/apps/cfm/src/main/java/org/onosproject/cfm/impl/package-info.java b/apps/cfm/src/main/java/org/onosproject/cfm/impl/package-info.java
new file mode 100644
index 0000000..798317d
--- /dev/null
+++ b/apps/cfm/src/main/java/org/onosproject/cfm/impl/package-info.java
@@ -0,0 +1,19 @@
+/*
+ * Copyright 2017-present Open Networking Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+/**
+ * REST Web Application for CFM.
+ */
+package org.onosproject.cfm.impl;
\ No newline at end of file
