diff --git a/netconf/nc_rpc/ext/voltha_rpc.py b/netconf/nc_rpc/ext/voltha_rpc.py
new file mode 100644
index 0000000..37ba305
--- /dev/null
+++ b/netconf/nc_rpc/ext/voltha_rpc.py
@@ -0,0 +1,117 @@
+#!/usr/bin/env python
+#
+# Copyright 2017 the original author or authors.
+#
+# 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.
+#
+import structlog
+from netconf.nc_rpc.rpc import Rpc
+import netconf.nc_common.error as ncerror
+from twisted.internet.defer import inlineCallbacks, returnValue
+import dicttoxml
+from netconf.nc_common.utils import qmap, ns
+from netconf.constants import Constants as C
+from netconf.grpc_client.nc_rpc_mapper import \
+    get_nc_rpc_mapper_instance
+
+log = structlog.get_logger()
+
+
+class VolthaRpc(Rpc):
+    def __init__(self, request, request_xml, grpc_client, session,
+                 capabilities):
+        super(VolthaRpc, self).__init__(request, request_xml, grpc_client,
+                                        session, capabilities)
+        self.service = None
+        self.method = None
+        self.metadata = None
+        self._extract_parameters()
+        if not self.rpc_response.is_error:
+            self._validate_parameters()
+
+    @inlineCallbacks
+    def execute(self):
+        if self.rpc_response.is_error:
+            returnValue(self.rpc_response)
+
+        log.info('voltha-rpc-request', session=self.session.session_id,
+                 request=self.request)
+
+        # Execute the request
+        res_dict = yield self.grpc_client.invoke_voltha_rpc(
+            service=self.service,
+            method=self.method,
+            params=self.request['params'],
+            metadata=self.metadata)
+
+        # convert dict to xml
+        xml = dicttoxml.dicttoxml(res_dict, attr_type=True)
+        log.info('voltha-info', res=res_dict, xml=xml)
+
+        root_elem = self.get_root_element(xml)
+
+        # Build the yang response
+        self.rpc_response.node = self.rpc_response.build_yang_response(
+            root_elem, self.request, custom_rpc=True)
+        self.rpc_response.is_error = False
+
+        returnValue(self.rpc_response)
+
+    def _validate_parameters(self):
+        log.info('validate-parameters', session=self.session.session_id)
+        # For now just validate that the command is presenf
+        if self.request:
+            try:
+                if self.request['command'] is None:
+                    self.rpc_response.is_error = True
+                    self.rpc_response.node = ncerror.BadMsg(self.request_xml)
+                    return
+
+            except Exception as e:
+                self.rpc_response.is_error = True
+                self.rpc_response.node = ncerror.ServerException(
+                    self.request_xml)
+                return
+
+    def _extract_parameters(self):
+        try:
+            rpc_node = self.request_xml.find(''.join(
+                [qmap(C.VOLTHA),
+                 self.request['command']])
+            )
+            self.request['params'] = {}
+            if rpc_node is not None:
+                for r in rpc_node:
+                    self.request['params'][
+                        r.tag.replace(qmap(C.VOLTHA), "")] = r.text
+
+            # Remove the subclass element in the request if it is present as
+            # it is not required for rpc calls
+            if self.request.has_key('subclass'):
+                self.request.pop('subclass', None)
+
+            # Extract the service and method from the rpc command
+            command = self.request['command'].split('-')
+            if len(command) != 2:
+                log.debug('invalid-format', command=self.request['command'])
+                raise
+
+            self.service = command[0]
+            self.method = command[1]
+            if self.request.has_key('metadata'):
+                self.metadata = self.request['metadata']
+
+        except Exception as e:
+            self.rpc_response.is_error = True
+            self.rpc_response.node = ncerror.BadMsg(self.request_xml)
+            log.exception('params-parsing-error', xml=self.request_xml, e=e)
