@@ -22,6 +22,7 @@ use omicron_common::api::external::Error;
22
22
use omicron_common:: api:: external:: ListResultVec ;
23
23
use omicron_common:: api:: internal:: nexus:: HostIdentifier ;
24
24
use omicron_common:: api:: internal:: shared:: NetworkInterface ;
25
+ use omicron_common:: api:: internal:: shared:: ResolvedVpcFirewallRule ;
25
26
use oxnet:: IpNet ;
26
27
use slog:: Logger ;
27
28
use slog:: debug;
@@ -48,7 +49,7 @@ pub async fn resolve_firewall_rules_for_sled_agent(
48
49
vpc : & db:: model:: Vpc ,
49
50
rules : & [ db:: model:: VpcFirewallRule ] ,
50
51
log : & Logger ,
51
- ) -> Result < Vec < sled_agent_client :: types :: ResolvedVpcFirewallRule > , Error > {
52
+ ) -> Result < Vec < ResolvedVpcFirewallRule > , Error > {
52
53
// Collect the names of instances, subnets, and VPCs that are either
53
54
// targets or host filters. We have to find the sleds for all the
54
55
// targets, and we'll need information about the IP addresses or
@@ -133,6 +134,7 @@ pub async fn resolve_firewall_rules_for_sled_agent(
133
134
}
134
135
135
136
let mut vpc_interfaces: NicMap = HashMap :: new ( ) ;
137
+ let mut vpc_vni_map = HashMap :: new ( ) ;
136
138
for vpc_name in & vpcs {
137
139
if let Ok ( ( .., authz_vpc) ) = LookupPath :: new ( opctx, datastore)
138
140
. project_id ( vpc. project_id )
@@ -144,6 +146,7 @@ pub async fn resolve_firewall_rules_for_sled_agent(
144
146
. derive_vpc_network_interface_info ( opctx, & authz_vpc)
145
147
. await ?
146
148
{
149
+ vpc_vni_map. insert ( & vpc_name. 0 , iface. vni ) ;
147
150
vpc_interfaces
148
151
. entry ( vpc_name. 0 . clone ( ) )
149
152
. or_insert_with ( Vec :: new)
@@ -328,7 +331,7 @@ pub async fn resolve_firewall_rules_for_sled_agent(
328
331
AllowedSourceIps :: List ( list) => Some (
329
332
list. iter ( )
330
333
. copied ( )
331
- . map ( |ip| HostIdentifier :: Ip ( ip ) . into ( ) )
334
+ . map ( HostIdentifier :: Ip )
332
335
. collect ( ) ,
333
336
) ,
334
337
}
@@ -355,50 +358,40 @@ pub async fn resolve_firewall_rules_for_sled_agent(
355
358
// There are host filters, but we don't need to apply the allowlist
356
359
// to this VPC either, so insert the rules as-is.
357
360
( Some ( hosts) , None ) => {
358
- let mut host_addrs = Vec :: with_capacity ( hosts. len ( ) ) ;
361
+ let mut host_addrs = HashSet :: with_capacity ( hosts. len ( ) ) ;
359
362
for host in hosts {
360
363
match & host. 0 {
361
364
external:: VpcFirewallRuleHostFilter :: Instance ( name) => {
362
365
for interface in instance_interfaces
363
366
. get ( & name)
364
367
. unwrap_or ( & no_interfaces)
365
368
{
366
- host_addrs. push (
367
- HostIdentifier :: Ip ( IpNet :: host_net (
368
- interface. ip ,
369
- ) )
370
- . into ( ) ,
371
- )
369
+ host_addrs. insert ( HostIdentifier :: Ip (
370
+ IpNet :: host_net ( interface. ip ) ,
371
+ ) ) ;
372
372
}
373
373
}
374
374
external:: VpcFirewallRuleHostFilter :: Subnet ( name) => {
375
375
for subnet in subnet_networks
376
376
. get ( name)
377
377
. unwrap_or ( & no_networks)
378
378
{
379
- host_addrs. push (
380
- HostIdentifier :: Ip ( IpNet :: from ( * subnet) )
381
- . into ( ) ,
382
- ) ;
379
+ host_addrs. insert ( HostIdentifier :: Ip (
380
+ IpNet :: from ( * subnet) ,
381
+ ) ) ;
383
382
}
384
383
}
385
384
external:: VpcFirewallRuleHostFilter :: Ip ( addr) => {
386
- host_addrs. push (
387
- HostIdentifier :: Ip ( IpNet :: host_net ( * addr) )
388
- . into ( ) ,
389
- )
385
+ host_addrs. insert ( HostIdentifier :: Ip (
386
+ IpNet :: host_net ( * addr) ,
387
+ ) ) ;
390
388
}
391
389
external:: VpcFirewallRuleHostFilter :: IpNet ( net) => {
392
- host_addrs. push ( HostIdentifier :: Ip ( * net) . into ( ) )
390
+ host_addrs. insert ( HostIdentifier :: Ip ( * net) ) ;
393
391
}
394
392
external:: VpcFirewallRuleHostFilter :: Vpc ( name) => {
395
- for interface in vpc_interfaces
396
- . get ( name)
397
- . unwrap_or ( & no_interfaces)
398
- {
399
- host_addrs. push (
400
- HostIdentifier :: Vpc ( interface. vni ) . into ( ) ,
401
- )
393
+ if let Some ( vni) = vpc_vni_map. get ( name) {
394
+ host_addrs. insert ( HostIdentifier :: Vpc ( * vni) ) ;
402
395
}
403
396
}
404
397
}
@@ -414,25 +407,23 @@ pub async fn resolve_firewall_rules_for_sled_agent(
414
407
let filter_ports = rule
415
408
. filter_ports
416
409
. as_ref ( )
417
- . map ( |ports| ports. iter ( ) . map ( |v| v. 0 . into ( ) ) . collect ( ) ) ;
410
+ . map ( |ports| ports. iter ( ) . map ( |v| v. 0 ) . collect ( ) ) ;
418
411
419
412
let filter_protocols = rule
420
413
. filter_protocols
421
414
. as_ref ( )
422
- . map ( |protocols| protocols. iter ( ) . map ( |v| v. 0 . into ( ) ) . collect ( ) ) ;
415
+ . map ( |protocols| protocols. iter ( ) . map ( |v| v. 0 ) . collect ( ) ) ;
423
416
424
- sled_agent_rules. push (
425
- sled_agent_client:: types:: ResolvedVpcFirewallRule {
426
- status : rule. status . 0 . into ( ) ,
427
- direction : rule. direction . 0 . into ( ) ,
428
- targets,
429
- filter_hosts,
430
- filter_ports,
431
- filter_protocols,
432
- action : rule. action . 0 . into ( ) ,
433
- priority : rule. priority . 0 . 0 ,
434
- } ,
435
- ) ;
417
+ sled_agent_rules. push ( ResolvedVpcFirewallRule {
418
+ status : rule. status . 0 ,
419
+ direction : rule. direction . 0 ,
420
+ targets,
421
+ filter_hosts,
422
+ filter_ports,
423
+ filter_protocols,
424
+ action : rule. action . 0 ,
425
+ priority : rule. priority . 0 ,
426
+ } ) ;
436
427
}
437
428
debug ! (
438
429
log,
0 commit comments