Merge "Allow keystone endpoint_type interpolation for Neutron models  - Add 'endpoint_type' identity parameter  - Set 'endpoint_type: internal' as a    default parameter for 'service' reclass model (/metadata/)"
diff --git a/README.rst b/README.rst
index 5ff5164..0fe54e5 100644
--- a/README.rst
+++ b/README.rst
@@ -510,6 +510,66 @@
             ovs:
               driver: openvswitch
 
+Neutron OVS DPDK
+==================
+
+Enable datapath netdev for neutron openvswitch agent
+
+.. code-block:: yaml
+
+    neutron:
+      server:
+        version: mitaka
+        ...
+        dpdk: True
+        ...
+
+    neutron:
+      compute:
+        version: mitaka
+        plugin: ml2
+        dpdk: True
+        backend:
+          engine: ml2
+          ...
+          mechanism:
+            ovs:
+              driver: openvswitch
+
+Neutron OVS SR-IOV
+==================
+
+.. code-block:: yaml
+
+    neutron:
+      server:
+        version: mitaka
+        plugin: ml2
+        backend:
+          engine: ml2
+          ...
+          mechanism:
+            ovs:
+              driver: openvswitch
+            sriov:
+              driver: sriovnicswitch
+
+    neutron:
+      compute:
+        version: mitaka
+        plugin: ml2
+        ...
+        backend:
+          engine: ml2
+          tenant_network_types: "flat,vlan" # Can be mixed flat,vlan,vxlan
+          sriov:
+            nic_one:
+              devname: eth1
+              physical_network: physnet3
+          mechanism:
+            ovs:
+              driver: openvswitch
+
 Neutron Server with OpenContrail
 ==================================
 
diff --git a/neutron/compute.sls b/neutron/compute.sls
index 057d40c..e67eac5 100644
--- a/neutron/compute.sls
+++ b/neutron/compute.sls
@@ -12,6 +12,35 @@
   - require:
     - pkg: neutron_compute_packages
 
+{% if compute.backend.sriov is defined %}
+
+neutron_sriov_package:
+  pkg.installed:
+  - name: neutron-sriov-agent
+
+/etc/neutron/plugins/ml2/sriov_agent.ini:
+  file.managed:
+  - source: salt://neutron/files/{{ compute.version }}/sriov_agent.ini
+  - template: jinja
+  - watch_in:
+    - service: neutron_compute_services
+  - require:
+    - pkg: neutron_compute_packages
+    - pkg: neutron_sriov_package
+
+neutron_sriov_service:
+  service.running:
+  - name: neutron-sriov-agent
+  - enable: true
+  - watch_in:
+    - service: neutron_compute_services
+  - watch:
+    - file: /etc/neutron/neutron.conf
+    - file: /etc/neutron/plugins/ml2/openvswitch_agent.ini
+    - file: /etc/neutron/plugins/ml2/sriov_agent.ini
+
+{% endif %}
+
 {% if compute.dvr %}
 
 neutron_dvr_packages:
diff --git a/neutron/files/mitaka/ml2_conf.ini b/neutron/files/mitaka/ml2_conf.ini
index a0879b1..67841f2 100644
--- a/neutron/files/mitaka/ml2_conf.ini
+++ b/neutron/files/mitaka/ml2_conf.ini
@@ -196,7 +196,11 @@
 
 # Driver for security groups firewall in the L2 agent (string value)
 #firewall_driver = <None>
+{%- if server.dpdk %}
+firewall_driver = openvswitch
+{%- else %}
 firewall_driver = neutron.agent.linux.iptables_firewall.OVSHybridIptablesFirewallDriver
+{%- endif %}
 
 # Controls whether the neutron security group API is enabled in the server. It should be false when using no security groups or using the
 # nova security group API. (boolean value)
diff --git a/neutron/files/mitaka/openvswitch_agent.ini b/neutron/files/mitaka/openvswitch_agent.ini
index 4656e35..b93aaeb 100644
--- a/neutron/files/mitaka/openvswitch_agent.ini
+++ b/neutron/files/mitaka/openvswitch_agent.ini
@@ -207,6 +207,9 @@
 # to 'netdev'. (string value)
 # Allowed values: system, netdev
 #datapath_type = system
+{%- if neutron.dpdk %}
+datapath_type = netdev
+{%- endif %}
 
 # OVS vhost-user socket directory. (string value)
 #vhostuser_socket_dir = /var/run/openvswitch
@@ -240,7 +243,11 @@
 
 # Driver for security groups firewall in the L2 agent (string value)
 #firewall_driver = <None>
+{%- if neutron.dpdk %}
+firewall_driver = openvswitch
+{%- else %}
 firewall_driver = neutron.agent.linux.iptables_firewall.OVSHybridIptablesFirewallDriver
+{%- endif %}
 
 # Controls whether the neutron security group API is enabled in the server. It should be false when using no security groups or using the
 # nova security group API. (boolean value)
diff --git a/neutron/files/mitaka/sriov_agent.ini b/neutron/files/mitaka/sriov_agent.ini
new file mode 100644
index 0000000..d4ac823
--- /dev/null
+++ b/neutron/files/mitaka/sriov_agent.ini
@@ -0,0 +1,45 @@
+{%- if pillar.neutron.gateway is defined %}
+{%- from "neutron/map.jinja" import gateway as neutron with context %}
+{%- else %}
+{%- from "neutron/map.jinja" import compute as neutron with context %}
+{%- endif %}
+[DEFAULT]
+
+#
+# From oslo.log
+#
+
+# If set to true, the logging level will be set to DEBUG instead of the default INFO level. (boolean value)
+#debug = false
+
+# If set to false, the logging level will be set to WARNING instead of the default INFO level. (boolean value)
+# This option is deprecated for removal.
+# Its value may be silently ignored in the future.
+#verbose = true
+
+[agent]
+
+#
+# From neutron.ml2.sriov.agent
+#
+
+# Extensions list to use (list value)
+#extensions =
+
+
+[ml2_sriov]
+
+#
+# From neutron.ml2.sriov.agent
+#
+
+# Comma-separated list of <physical_network>:<network_device> tuples mapping physical network names to the agent's node-specific physical
+# network device interfaces of SR-IOV physical function to be used for VLAN networks. All physical networks listed in network_vlan_ranges on
+# the server should have mappings to appropriate interfaces on each agent. (list value)
+#physical_device_mappings =
+physical_device_mappings = {%- for nic_name, sriov in neutron.backend.sriov.iteritems() %}{{ sriov.physical_network }}:{{ sriov.devname }}{% if not loop.last %},{% endif %}{%- endfor %}
+
+# Comma-separated list of <network_device>:<vfs_to_exclude> tuples, mapping network_device to the agent's node-specific list of virtual
+# functions that should not be used for virtual networking. vfs_to_exclude is a semicolon-separated list of virtual functions to exclude
+# from network_device. The network_device in the mapping should appear in the physical_device_mappings list. (list value)
+#exclude_devices =
diff --git a/neutron/map.jinja b/neutron/map.jinja
index d00f754..795c4ce 100644
--- a/neutron/map.jinja
+++ b/neutron/map.jinja
@@ -3,6 +3,7 @@
     'Debian': {
         'pkgs': ['neutron-openvswitch-agent', 'openvswitch-switch', 'python-pycadf'],
         'services': ['neutron-openvswitch-agent'],
+        'dpdk': false,
         'audit': {
           'enabled': false
         }
@@ -10,6 +11,7 @@
     'RedHat': {
         'pkgs': ['openstack-neutron-openvswitch', 'openvswitch', 'python-pycadf'],
         'services': ['neutron-openvswitch-agent'],
+        'dpdk': false,
         'audit': {
           'enabled': false
         }
@@ -19,11 +21,13 @@
 {% set gateway = salt['grains.filter_by']({
     'Debian': {
         'pkgs': ['neutron-dhcp-agent', 'neutron-openvswitch-agent', 'neutron-l3-agent', 'openvswitch-common', 'neutron-metadata-agent'],
-        'services': ['neutron-openvswitch-agent', 'neutron-metadata-agent', 'neutron-l3-agent', 'neutron-dhcp-agent']
+        'services': ['neutron-openvswitch-agent', 'neutron-metadata-agent', 'neutron-l3-agent', 'neutron-dhcp-agent'],
+        'dpdk': false
     },
     'RedHat': {
         'pkgs': ['openstack-neutron-openvswitch'],
-        'services': ['neutron-openvswitch-agent', 'neutron-metadata-agent', 'neutron-l3-agent', 'neutron-dhcp-agent']
+        'services': ['neutron-openvswitch-agent', 'neutron-metadata-agent', 'neutron-l3-agent', 'neutron-dhcp-agent'],
+        'dpdk': false
     },
 }, merge=pillar.neutron.get('gateway', {})) %}
 
@@ -33,6 +37,7 @@
         'pkgs_ml2': ['neutron-plugin-ml2'],
         'services': ['neutron-server'],
         'notification': False,
+        'dpdk': false,
         'audit': {
           'enabled': false
         }
@@ -42,6 +47,7 @@
         'pkgs': ['openstack-neutron'],
         'services': ['neutron-server'],
         'notification': False,
+        'dpdk': false,
         'audit': {
           'enabled': false
         }
diff --git a/tests/pillar/compute_dpdk.sls b/tests/pillar/compute_dpdk.sls
new file mode 100644
index 0000000..0a3a498
--- /dev/null
+++ b/tests/pillar/compute_dpdk.sls
@@ -0,0 +1,25 @@
+neutron:
+  compute:
+    agent_mode: legacy
+    dpdk: True
+    backend:
+      engine: ml2
+      tenant_network_types: "flat,vlan"
+      mechanism:
+        ovs:
+          driver: openvswitch
+    dvr: false
+    enabled: true
+    external_access: false
+    local_ip: 10.1.0.105
+    message_queue:
+      engine: rabbitmq
+      host: 172.16.10.254
+      password: workshop
+      port: 5672
+      user: openstack
+      virtual_host: /openstack
+    metadata:
+      host: 172.16.10.254
+      password: password
+    version: mitaka
diff --git a/tests/pillar/compute_sriov.sls b/tests/pillar/compute_sriov.sls
new file mode 100644
index 0000000..9504878
--- /dev/null
+++ b/tests/pillar/compute_sriov.sls
@@ -0,0 +1,28 @@
+neutron:
+  compute:
+    agent_mode: legacy
+    backend:
+      engine: ml2
+      tenant_network_types: "flat,vxlan"
+      sriov:
+        nic_one:
+          devname: eth1
+          physical_network: physnet3
+      mechanism:
+        ovs:
+          driver: openvswitch
+    dvr: false
+    enabled: true
+    external_access: false
+    local_ip: 10.1.0.105
+    message_queue:
+      engine: rabbitmq
+      host: 172.16.10.254
+      password: workshop
+      port: 5672
+      user: openstack
+      virtual_host: /openstack
+    metadata:
+      host: 172.16.10.254
+      password: password
+    version: mitaka