Add PCI Passthrough/SR-IOV support

The main issue with INI files, it doesn't support complex structures
which end up being declared as strings. This approach get that chain of
character and verify it's a valid JSON equivalent before assigning the
value.

Another driver is even though Hiera supports complex structure, we tend
to keep it simple when using Hiera interpolations.

https://wiki.openstack.org/wiki/SR-IOV-Passthrough-For-Networking#SR-IOV_Configuration

Change-Id: I27d43af13fcc80f41a16c31a0a6cfe112dc96acb
This commit is contained in:
Gilles Dubreuil 2015-02-06 23:22:09 +11:00
parent 6fadda9561
commit c671ad7d25
5 changed files with 67 additions and 1 deletions

View File

@ -0,0 +1,27 @@
require 'json'
def array_of_hash?(list)
return false unless !list.empty? && list.class == Array
list.each do |e|
return false unless e.class == Hash
end
true
end
module Puppet::Parser::Functions
newfunction(:check_array_of_hash, :arity =>1, :type => :rvalue, :doc => "Check
input String is a valid Array of Hash in JSON style") do |arg|
if arg[0].class == String
begin
list = JSON.load(arg[0].gsub("'","\""))
rescue JSON::ParserError
raise Puppet::ParseError, "Syntax error: #{arg[0]} is invalid"
else
return arg[0] if array_of_hash?(list)
end
else
raise Puppet::ParseError, "Syntax error: #{arg[0]} is not a String"
end
return ''
end
end

View File

@ -102,6 +102,12 @@
# (optional) Shared secret to validate proxies Neutron metadata requests
# Defaults to undef
#
# [*pci_alias*]
# (optional) Pci passthrough for controller:
# Defaults to undef
# Example
# "[ {'vendor_id':'1234', 'product_id':'5678', 'name':'default'}, {...} ]"
#
# [*ratelimits*]
# (optional) A string that is a semicolon-separated list of 5-tuples.
# See http://docs.openstack.org/trunk/config-reference/content/configuring-compute-API.html
@ -161,6 +167,7 @@ class nova::api(
$sync_db = true,
$neutron_metadata_proxy_shared_secret = undef,
$osapi_v3 = false,
$pci_alias = undef,
$ratelimits = undef,
$ratelimits_factory =
'nova.api.openstack.compute.limits:RateLimitingMiddleware.factory',
@ -319,6 +326,12 @@ class nova::api(
'filter:authtoken/auth_admin_prefix': ensure => absent;
}
if $pci_alias {
nova_config {
'DEFAULT/pci_alias': value => check_array_of_hash($pci_alias);
}
}
if $validate {
$defaults = {
'nova-api' => {
@ -328,5 +341,4 @@ class nova::api(
$validation_options_hash = merge ($defaults, $validation_options)
create_resources('openstacklib::service_validation', $validation_options_hash, {'subscribe' => 'Service[nova-api]'})
}
}

View File

@ -99,6 +99,13 @@
# (optional) The availability zone to show internal services under.
# Defaults to internal
#
# [*pci_passthrough_whitelist*]
# (optional) Pci passthrough hash in format of:
# Defaults to undef
# Example
# "[ { 'vendor_id':'1234','product_id':'5678' },
# { 'vendor_id':'4321','product_id':'8765','physical_network':'default' } ] "
#
class nova::compute (
$enabled = false,
$manage_service = true,
@ -123,6 +130,7 @@ class nova::compute (
$default_schedule_zone = undef,
$internal_service_availability_zone = 'internal',
$heal_instance_info_cache_interval = '60',
$pci_passthrough = undef,
) {
include nova::params
@ -218,4 +226,9 @@ class nova::compute (
}
}
if ($pci_passthrough) {
nova_config {
'DEFAULT/pci_passthrough_whitelist': value => check_array_of_hash($pci_passthrough);
}
}
}

View File

@ -99,6 +99,7 @@ describe 'nova::api' do
:metadata_workers => 2,
:osapi_v3 => true,
:keystone_ec2_url => 'https://example.com:5000/v2.0/ec2tokens',
:pci_alias => "[{\"vendor_id\":\"8086\",\"product_id\":\"0126\",\"name\":\"graphic_card\"},{\"vendor_id\":\"9096\",\"product_id\":\"1520\",\"name\":\"network_card\"}]"
})
end
@ -155,6 +156,12 @@ describe 'nova::api' do
it 'configure nova api v3' do
should contain_nova_config('osapi_v3/enabled').with('value' => true)
end
it 'configures nova pci_alias entries' do
should contain_nova_config('DEFAULT/pci_alias').with(
'value' => "[{\"vendor_id\":\"8086\",\"product_id\":\"0126\",\"name\":\"graphic_card\"},{\"vendor_id\":\"9096\",\"product_id\":\"1520\",\"name\":\"network_card\"}]"
)
end
end
[

View File

@ -58,6 +58,7 @@ describe 'nova::compute' do
:default_schedule_zone => 'az2',
:internal_service_availability_zone => 'az_int1',
:heal_instance_info_cache_interval => '120',
:pci_passthrough => "[{\"vendor_id\":\"8086\",\"product_id\":\"0126\"},{\"vendor_id\":\"9096\",\"product_id\":\"1520\",\"physical_network\":\"physnet1\"}]"
}
end
@ -101,6 +102,12 @@ describe 'nova::compute' do
it { should contain_nova_config('DEFAULT/heal_instance_info_cache_interval').with_value('120') }
it { should contain_nova_config('DEFAULT/force_raw_images').with(:value => false) }
it 'configures nova pci_passthrough_whitelist entries' do
should contain_nova_config('DEFAULT/pci_passthrough_whitelist').with(
'value' => "[{\"vendor_id\":\"8086\",\"product_id\":\"0126\"},{\"vendor_id\":\"9096\",\"product_id\":\"1520\",\"physical_network\":\"physnet1\"}]"
)
end
end
context 'with neutron_enabled set to false' do