2 * Copyright (c) 2014 Cisco Systems, Inc. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
9 package org.opendaylight.groupbasedpolicy.neutron.mapper.mapping.rule;
11 import static com.google.common.base.Preconditions.checkNotNull;
13 import java.util.HashMap;
14 import java.util.List;
17 import java.util.stream.Collector;
18 import java.util.stream.Collectors;
20 import javax.annotation.Nonnull;
22 import org.opendaylight.controller.config.yang.config.neutron_mapper.impl.NeutronMapperModule;
23 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
24 import org.opendaylight.controller.md.sal.binding.api.ReadWriteTransaction;
25 import org.opendaylight.controller.md.sal.binding.api.WriteTransaction;
26 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
27 import org.opendaylight.groupbasedpolicy.api.sf.ChainActionDefinition;
28 import org.opendaylight.groupbasedpolicy.dto.EpgKeyDto;
29 import org.opendaylight.groupbasedpolicy.neutron.mapper.mapping.NeutronAware;
30 import org.opendaylight.groupbasedpolicy.neutron.mapper.mapping.NeutronSecurityGroupAware;
31 import org.opendaylight.groupbasedpolicy.neutron.mapper.util.MappingUtils;
32 import org.opendaylight.groupbasedpolicy.neutron.mapper.util.SecurityGroupUtils;
33 import org.opendaylight.groupbasedpolicy.neutron.mapper.util.SecurityRuleUtils;
34 import org.opendaylight.groupbasedpolicy.util.DataStoreHelper;
35 import org.opendaylight.groupbasedpolicy.util.IidFactory;
36 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.Uuid;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.common.rev140421.ActionName;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.common.rev140421.ClauseName;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.common.rev140421.ContractId;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.common.rev140421.Description;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.common.rev140421.EndpointGroupId;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.common.rev140421.ParameterName;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.common.rev140421.SelectorName;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.common.rev140421.TenantId;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.neutron.gbp.mapper.rev150513.change.action.of.security.group.rules.input.action.ActionChoice;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.neutron.gbp.mapper.rev150513.change.action.of.security.group.rules.input.action.action.choice.SfcActionCase;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.HasDirection.Direction;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.subject.feature.instance.ParameterValueBuilder;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.tenants.tenant.policy.Contract;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.tenants.tenant.policy.endpoint.group.ConsumerNamedSelector;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.tenants.tenant.policy.endpoint.group.ConsumerNamedSelectorBuilder;
52 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.tenants.tenant.policy.endpoint.group.ProviderNamedSelector;
53 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.tenants.tenant.policy.endpoint.group.ProviderNamedSelectorBuilder;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.tenants.tenant.policy.subject.feature.instances.ActionInstance;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.tenants.tenant.policy.subject.feature.instances.ActionInstanceBuilder;
56 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.policy.rev140421.tenants.tenant.policy.subject.feature.instances.ClassifierInstance;
57 import org.opendaylight.yang.gen.v1.urn.opendaylight.neutron.rev150712.Neutron;
58 import org.opendaylight.yang.gen.v1.urn.opendaylight.neutron.secgroups.rev150712.security.groups.attributes.security.groups.SecurityGroup;
59 import org.opendaylight.yang.gen.v1.urn.opendaylight.neutron.secgroups.rev150712.security.groups.attributes.security.groups.SecurityGroupKey;
60 import org.opendaylight.yang.gen.v1.urn.opendaylight.neutron.secgroups.rev150712.security.rules.attributes.SecurityRules;
61 import org.opendaylight.yang.gen.v1.urn.opendaylight.neutron.secgroups.rev150712.security.rules.attributes.security.rules.SecurityRule;
62 import org.opendaylight.yang.gen.v1.urn.opendaylight.neutron.secgroups.rev150712.security.rules.attributes.security.rules.SecurityRuleKey;
63 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
64 import org.slf4j.Logger;
65 import org.slf4j.LoggerFactory;
67 import com.google.common.annotations.VisibleForTesting;
68 import com.google.common.base.Optional;
69 import com.google.common.base.Preconditions;
70 import com.google.common.collect.HashMultiset;
71 import com.google.common.collect.ImmutableList;
72 import com.google.common.collect.Multiset;
73 import com.google.common.collect.Sets;
75 public class NeutronSecurityRuleAware implements NeutronAware<SecurityRule> {
77 private static final Logger LOG = LoggerFactory.getLogger(NeutronSecurityRuleAware.class);
78 public static final InstanceIdentifier<SecurityRule> SECURITY_RULE_WILDCARD_IID =
79 InstanceIdentifier.builder(Neutron.class).child(SecurityRules.class).child(SecurityRule.class).build();
80 private static final String CONTRACT_PROVIDER = "Contract provider: ";
81 private final DataBroker dataProvider;
82 private final Multiset<InstanceIdentifier<ClassifierInstance>> createdClassifierInstances;
83 private final Multiset<InstanceIdentifier<ActionInstance>> createdActionInstances;
84 private final Map<SecurityRuleKey, SecurityRule> pendingCreatedRules;
85 private final Map<SecurityGroupKey, SecurityGroup> pendingDeletedGroups;
86 final static String PROVIDED_BY = "provided_by-";
87 final static String POSSIBLE_CONSUMER = "possible_consumer-";
89 public NeutronSecurityRuleAware(DataBroker dataProvider) {
90 this(dataProvider, HashMultiset.<InstanceIdentifier<ClassifierInstance>>create(),
91 HashMultiset.<InstanceIdentifier<ActionInstance>>create());
95 NeutronSecurityRuleAware(DataBroker dataProvider,
96 Multiset<InstanceIdentifier<ClassifierInstance>> classifierInstanceNames,
97 Multiset<InstanceIdentifier<ActionInstance>> createdActionInstances) {
98 this.dataProvider = checkNotNull(dataProvider);
99 this.createdClassifierInstances = checkNotNull(classifierInstanceNames);
100 this.createdActionInstances = checkNotNull(createdActionInstances);
101 this.pendingCreatedRules = new HashMap<>();
102 this.pendingDeletedGroups = new HashMap<>();
106 public void onCreated(SecurityRule secRule, Neutron neutron) {
107 LOG.trace("created securityRule - {}", secRule);
108 if (neutron.getSecurityGroups() == null || neutron.getSecurityGroups().getSecurityGroup() == null
109 || !neutron.getSecurityGroups()
112 .filter(sg -> sg.getKey().getUuid().equals(secRule.getSecurityGroupId()))
115 pendingCreatedRules.put(secRule.getKey(), secRule);
116 LOG.warn("Security group of security rule {} does not exist yet. The rule will be processed"
117 + "when the missing security group is created.", secRule.getKey());
120 ReadWriteTransaction rwTx = dataProvider.newReadWriteTransaction();
121 boolean isNeutronSecurityRuleAdded = addNeutronSecurityRule(secRule, neutron, rwTx);
122 if (isNeutronSecurityRuleAdded) {
123 DataStoreHelper.submitToDs(rwTx);
129 public void flushPendingSecurityRulesFor(@Nonnull SecurityGroupKey secGroupKey, Neutron neutron) {
130 List<SecurityRule> rules = pendingCreatedRules.values()
132 .filter(sr -> sr.getSecurityGroupId().equals(secGroupKey.getUuid()))
133 .collect(Collectors.toList());
134 rules.forEach(sr -> {
135 LOG.trace("Flushing pending security rule {}", sr);
136 ReadWriteTransaction rwTx = dataProvider.newReadWriteTransaction();
137 boolean isNeutronSecurityRuleAdded = addNeutronSecurityRule(sr, neutron, rwTx);
138 if (isNeutronSecurityRuleAdded) {
139 DataStoreHelper.submitToDs(rwTx);
143 pendingCreatedRules.remove(sr.getKey());
147 public boolean addNeutronSecurityRule(SecurityRule secRule, Neutron neutron, ReadWriteTransaction rwTx) {
148 return addNeutronSecurityRuleWithAction(secRule, neutron, MappingUtils.ALLOW_ACTION_CHOICE, rwTx);
151 public boolean addNeutronSecurityRuleWithAction(SecurityRule secRule, Neutron neutron, ActionChoice action,
152 ReadWriteTransaction rwTx) {
153 TenantId tenantId = new TenantId(secRule.getTenantId().getValue());
154 Uuid providerSecGroupId = secRule.getSecurityGroupId();
155 EndpointGroupId providerEpgId = new EndpointGroupId(providerSecGroupId.getValue());
157 Description contractDescription = createContractDescription(secRule, neutron);
158 SingleRuleContract singleRuleContract = createSingleRuleContract(secRule, contractDescription, action);
159 Contract contract = singleRuleContract.getContract();
160 rwTx.put(LogicalDatastoreType.CONFIGURATION, IidFactory.contractIid(tenantId, contract.getId()), contract, true);
161 SelectorName providerSelector = getSelectorNameWithConsumer(secRule, neutron);
162 writeProviderNamedSelectorToEpg(providerSelector, contract.getId(), new EpgKeyDto(providerEpgId, tenantId), rwTx);
164 if (secRule.getRemoteGroupId() != null) {
165 Uuid consumerSecGroupId = secRule.getRemoteGroupId();
166 designContractsBetweenProviderAndConsumer(tenantId, providerSecGroupId, consumerSecGroupId, neutron, rwTx);
167 designContractsBetweenProviderAndConsumer(tenantId, consumerSecGroupId, providerSecGroupId, neutron, rwTx);
169 for (Uuid consumerSecGroupId : SecurityRuleUtils.findSecurityGroupsHavingSecurityRules(neutron)) {
170 designContractsBetweenProviderAndConsumer(tenantId, providerSecGroupId, consumerSecGroupId, neutron, rwTx);
171 designContractsBetweenProviderAndConsumer(tenantId, consumerSecGroupId, providerSecGroupId, neutron, rwTx);
175 ClassifierInstance classifierInstance = singleRuleContract.getSingleClassifierRule().getClassifierInstance();
176 createClassifierInstanceIfNotExists(tenantId, classifierInstance, rwTx);
177 createAllowActionInstanceIfNotExists(tenantId, rwTx);
182 static Description createContractDescription(SecurityRule secRule, Neutron neutron) {
183 if (NeutronMapperModule.isDebugEnabled()) {
184 Optional<SecurityGroup> providerSecGroup =
185 SecurityGroupUtils.findSecurityGroup(secRule.getSecurityGroupId(), neutron.getSecurityGroups());
186 if (!providerSecGroup.isPresent()) {
187 LOG.error("Neutron Security Group with UUID {} does not exist but it is in {}", secRule.getSecurityGroupId().getValue(),
189 throw new IllegalStateException(
190 "Neutron Security Group with UUID " + secRule.getSecurityGroupId().getValue() + " does not exist.");
192 return new Description(CONTRACT_PROVIDER + SecurityGroupUtils.getNameOrUuid(providerSecGroup.get()));
195 return new Description(CONTRACT_PROVIDER + secRule.getSecurityGroupId());
199 static SingleRuleContract createSingleRuleContract(SecurityRule secRule, Description contractDescription, ActionChoice action) {
200 if (secRule.getRemoteIpPrefix() != null) {
201 return new SingleRuleContract(secRule, 0, contractDescription, action);
203 return new SingleRuleContract(secRule, 400, contractDescription, action);
207 void designContractsBetweenProviderAndConsumer(TenantId tenantId, Uuid provSecGroupId, Uuid consSecGroupId,
208 Neutron neutron, ReadWriteTransaction rwTx) {
209 Set<SecurityRule> provSecRules = getProvidedSecRulesBetween(provSecGroupId, consSecGroupId, neutron);
210 Set<SecurityRule> consSecRules = getProvidedSecRulesBetween(consSecGroupId, provSecGroupId, neutron);
211 EndpointGroupId consEpgId = new EndpointGroupId(consSecGroupId.getValue());
212 for (SecurityRule provSecRule : provSecRules) {
213 if (isProviderSecRuleSuitableForConsumerSecRules(provSecRule, consSecRules)) {
214 SelectorName consumerSelector = getSelectorNameWithProvider(provSecRule, neutron);
215 ContractId contractId = SecRuleEntityDecoder.getContractId(provSecRule);
216 writeConsumerNamedSelectorToEpg(consumerSelector, contractId, new EpgKeyDto(consEpgId, tenantId), rwTx);
218 // TODO add case when port ranges overlap
223 Set<SecurityRule> getProvidedSecRulesBetween(Uuid provSecGroup, Uuid consSecGroup, Neutron neutron) {
224 return Sets.union(SecurityRuleUtils.findSecurityRulesBySecGroupAndRemoteSecGroup(provSecGroup, consSecGroup, neutron),
225 SecurityRuleUtils.findSecurityRulesBySecGroupAndRemoteSecGroup(provSecGroup, null, neutron));
229 static boolean isProviderSecRuleSuitableForConsumerSecRules(SecurityRule provSecRule,
230 Set<SecurityRule> consSecRules) {
231 Direction directionProvSecRule = SecRuleEntityDecoder.getDirection(provSecRule);
232 for (SecurityRule consSecRule : consSecRules) {
233 Direction directionConsSecRule = SecRuleEntityDecoder.getDirection(consSecRule);
234 if (isDirectionOpposite(directionProvSecRule, directionConsSecRule)
235 && isOneWithinTwo(provSecRule, consSecRule)) {
242 public boolean changeActionOfNeutronSecurityRule(SecurityRule secRule, ActionChoice action, Neutron neutron, ReadWriteTransaction rwTx) {
243 addSfcChainActionInstance(action, new TenantId(secRule.getTenantId().getValue()), rwTx);
244 LOG.trace("Changing to action {} for secuirity group rule {}", action, secRule);
245 return addNeutronSecurityRuleWithAction(secRule, neutron, action, rwTx);
248 private void addSfcChainActionInstance(ActionChoice action, TenantId tenantId, ReadWriteTransaction rwTx) {
249 if (action instanceof SfcActionCase) {
250 String sfcChainName = ((SfcActionCase) action).getSfcChainName();
251 ActionName actionName = new ActionName(sfcChainName);
252 ActionInstance sfcActionInstance = new ActionInstanceBuilder().setName(actionName)
253 .setActionDefinitionId(ChainActionDefinition.ID)
255 ImmutableList.of(new ParameterValueBuilder().setName(
256 new ParameterName(ChainActionDefinition.SFC_CHAIN_NAME))
257 .setStringValue(sfcChainName)
260 rwTx.put(LogicalDatastoreType.CONFIGURATION, IidFactory.actionInstanceIid(tenantId, actionName),
261 sfcActionInstance, true);
265 private void writeProviderNamedSelectorToEpg(SelectorName providerSelector, ContractId contractId, EpgKeyDto epgKey,
266 WriteTransaction wTx) {
267 ProviderNamedSelector providerNamedSelector = new ProviderNamedSelectorBuilder().setName(providerSelector)
268 .setContract(ImmutableList.of(contractId))
270 wTx.put(LogicalDatastoreType.CONFIGURATION,
271 IidFactory.providerNamedSelectorIid(epgKey.getTenantId(), epgKey.getEpgId(),
272 providerNamedSelector.getName()), providerNamedSelector, true);
275 private void writeConsumerNamedSelectorToEpg(SelectorName consumerSelector, ContractId contractId, EpgKeyDto epgKey,
276 WriteTransaction wTx) {
277 ConsumerNamedSelector consumerNamedSelector = new ConsumerNamedSelectorBuilder().setName(consumerSelector)
278 .setContract(ImmutableList.of(contractId))
280 wTx.put(LogicalDatastoreType.CONFIGURATION,
281 IidFactory.consumerNamedSelectorIid(epgKey.getTenantId(), epgKey.getEpgId(),
282 consumerNamedSelector.getName()), consumerNamedSelector, true);
286 void createClassifierInstanceIfNotExists(TenantId tenantId, ClassifierInstance classifierInstance,
287 WriteTransaction wTx) {
288 InstanceIdentifier<ClassifierInstance> classifierInstanceIid = IidFactory.classifierInstanceIid(tenantId,
289 classifierInstance.getName());
290 if (!createdClassifierInstances.contains(classifierInstanceIid)) {
291 wTx.put(LogicalDatastoreType.CONFIGURATION, classifierInstanceIid, classifierInstance, true);
293 createdClassifierInstances.add(classifierInstanceIid);
297 void createAllowActionInstanceIfNotExists(TenantId tenantId, ReadWriteTransaction rwTx) {
298 InstanceIdentifier<ActionInstance> actionInstanceIid = IidFactory.actionInstanceIid(tenantId,
299 MappingUtils.ACTION_ALLOW.getName());
300 if (!createdActionInstances.contains(actionInstanceIid)) {
301 rwTx.put(LogicalDatastoreType.CONFIGURATION, actionInstanceIid, MappingUtils.ACTION_ALLOW, true);
303 createdActionInstances.add(actionInstanceIid);
307 public void onUpdated(SecurityRule oldSecRule, SecurityRule newSecRule, Neutron oldNeutron, Neutron newNeutron) {
308 LOG.warn("updated securityRule - Never should be called "
309 + "- neutron API does not allow UPDATE on neutron security group rule. \nSecurity group rule: {}",
313 public void addPendingDeletedSecGroup(SecurityGroup secGroup) {
314 LOG.trace("Caching pending deleted security group {}", secGroup.getKey());
315 pendingDeletedGroups.put(secGroup.getKey(), secGroup);
319 public void onDeleted(SecurityRule deletedSecRule, Neutron oldNeutron, Neutron newNeutron) {
320 LOG.trace("deleted securityRule - {}", deletedSecRule);
321 ReadWriteTransaction rwTx = dataProvider.newReadWriteTransaction();
322 boolean isNeutronSecurityRuleDeleted = deleteNeutronSecurityRule(deletedSecRule, oldNeutron, rwTx);
323 if (isNeutronSecurityRuleDeleted) {
324 DataStoreHelper.submitToDs(rwTx);
325 if (newNeutron == null || newNeutron.getSecurityRules() == null
326 || newNeutron.getSecurityRules().getSecurityRule() == null
327 || !newNeutron.getSecurityRules()
330 .filter(rule -> rule.getSecurityGroupId().equals(deletedSecRule.getSecurityGroupId()))
333 SecurityGroupKey secGroupKey = new SecurityGroupKey(deletedSecRule.getSecurityGroupId());
334 SecurityGroup pendingSg = pendingDeletedGroups.get(secGroupKey);
335 if (pendingSg != null) {
336 LOG.trace("Processing pending deleted security group {}", secGroupKey);
337 NeutronSecurityGroupAware.deleteGbpEndpointGroup(dataProvider,
338 new TenantId(deletedSecRule.getTenantId().getValue()),
339 new EndpointGroupId(secGroupKey.getUuid().getValue()));
340 pendingDeletedGroups.remove(secGroupKey);
348 public boolean deleteNeutronSecurityRule(SecurityRule secRule, Neutron neutron, ReadWriteTransaction rwTx) {
349 TenantId tenantId = new TenantId(secRule.getTenantId().getValue());
350 Uuid providerSecGroupId = secRule.getSecurityGroupId();
351 EndpointGroupId providerEpgId = new EndpointGroupId(providerSecGroupId.getValue());
353 SelectorName providerSelector = getSelectorNameWithConsumer(secRule, neutron);
354 deleteProviderNamedSelectorFromEpg(providerSelector, new EpgKeyDto(providerEpgId, tenantId), rwTx);
356 if (secRule.getRemoteGroupId() != null) {
357 Uuid consumerSecGroupId = secRule.getRemoteGroupId();
358 undesignContractsBetweenProviderAndConsumer(tenantId, providerSecGroupId, consumerSecGroupId, secRule, neutron, rwTx);
359 undesignContractsBetweenProviderAndConsumer(tenantId, consumerSecGroupId, providerSecGroupId, secRule, neutron, rwTx);
361 for (Uuid consumerSecGroupId : SecurityRuleUtils.findSecurityGroupsHavingSecurityRules(neutron)) {
362 undesignContractsBetweenProviderAndConsumer(tenantId, providerSecGroupId, consumerSecGroupId, secRule, neutron, rwTx);
363 undesignContractsBetweenProviderAndConsumer(tenantId, consumerSecGroupId, providerSecGroupId, secRule, neutron, rwTx);
367 ContractId contractId = SecRuleEntityDecoder.getContractId(secRule);
368 rwTx.delete(LogicalDatastoreType.CONFIGURATION, IidFactory.contractIid(tenantId, contractId));
370 ClassifierInstance classifierInstance = SecRuleEntityDecoder.getClassifierInstance(secRule);
371 deleteClassifierInstanceIfNotUsed(tenantId, classifierInstance, rwTx);
376 void undesignContractsBetweenProviderAndConsumer(TenantId tenantId, Uuid provSecGroupId,
377 Uuid consSecGroupId, SecurityRule removedSecRule, Neutron neutron, ReadWriteTransaction rwTx) {
378 Set<SecurityRule> provSecRules = getProvidedSecRulesBetween(provSecGroupId, consSecGroupId, neutron);
379 Set<SecurityRule> consSecRules = getProvidedSecRulesBetween(consSecGroupId, provSecGroupId, neutron);
380 EndpointGroupId consEpgId = new EndpointGroupId(consSecGroupId.getValue());
381 for (SecurityRule provSecRule : provSecRules) {
382 if (isProvidersSecRuleSuitableForConsumersSecRulesAndGoodToRemove(provSecRule, consSecRules, removedSecRule)) {
383 SelectorName consumerSelector = getSelectorNameWithProvider(provSecRule, neutron);
384 deleteConsumerNamedSelector(consumerSelector, new EpgKeyDto(consEpgId, tenantId), rwTx);
386 // TODO add case when port ranges overlap
391 static boolean isProvidersSecRuleSuitableForConsumersSecRulesAndGoodToRemove(SecurityRule provSecRule,
392 Set<SecurityRule> consSecRules, SecurityRule removedSecRule) {
393 Direction directionProvSecRule = SecRuleEntityDecoder.getDirection(provSecRule);
394 for (SecurityRule consSecRule : consSecRules) {
395 if (isRuleIdEqual(removedSecRule, consSecRule) || isRuleIdEqual(removedSecRule, provSecRule)) {
396 Direction directionConsSecRule = SecRuleEntityDecoder.getDirection(consSecRule);
397 if (isDirectionOpposite(directionProvSecRule, directionConsSecRule)
398 && isOneWithinTwo(provSecRule, consSecRule)) {
407 static boolean isRuleIdEqual(SecurityRule one, SecurityRule two) {
410 return one.getSecurityGroupId().equals(two.getSecurityGroupId());
413 private void deleteProviderNamedSelectorFromEpg(SelectorName providerSelector, EpgKeyDto providerEpgKey,
414 ReadWriteTransaction rwTx) {
415 InstanceIdentifier<ProviderNamedSelector> providerSelectorIid = IidFactory.providerNamedSelectorIid(
416 providerEpgKey.getTenantId(), providerEpgKey.getEpgId(), providerSelector);
417 DataStoreHelper.removeIfExists(LogicalDatastoreType.CONFIGURATION, providerSelectorIid, rwTx);
420 private void deleteConsumerNamedSelector(SelectorName consumerSelector, EpgKeyDto consumerEpgKey,
421 ReadWriteTransaction rwTx) {
422 InstanceIdentifier<ConsumerNamedSelector> consumerSelectorIid = IidFactory.consumerNamedSelectorIid(
423 consumerEpgKey.getTenantId(), consumerEpgKey.getEpgId(), consumerSelector);
424 DataStoreHelper.removeIfExists(LogicalDatastoreType.CONFIGURATION, consumerSelectorIid, rwTx);
427 private void deleteClassifierInstanceIfNotUsed(TenantId tenantId, ClassifierInstance classifierInstance,
428 ReadWriteTransaction rwTx) {
429 InstanceIdentifier<ClassifierInstance> classifierInstanceIid = IidFactory.classifierInstanceIid(tenantId,
430 classifierInstance.getName());
431 createdClassifierInstances.remove(classifierInstanceIid);
432 if (!createdClassifierInstances.contains(classifierInstanceIid)) {
433 DataStoreHelper.removeIfExists(LogicalDatastoreType.CONFIGURATION, classifierInstanceIid, rwTx);
438 void deleteAllowActionInstanceIfNotUsed(TenantId tenantId, ReadWriteTransaction rwTx) {
439 InstanceIdentifier<ActionInstance> actionInstanceIid = IidFactory.actionInstanceIid(tenantId,
440 MappingUtils.ACTION_ALLOW.getName());
441 createdActionInstances.remove(actionInstanceIid);
442 if (!createdActionInstances.contains(actionInstanceIid)) {
443 DataStoreHelper.removeIfExists(LogicalDatastoreType.CONFIGURATION, actionInstanceIid, rwTx);
447 private SelectorName getSelectorNameWithConsumer(SecurityRule secRule, Neutron neutron) {
448 ClauseName clauseName = SecRuleNameDecoder.getClauseName(secRule);
449 StringBuilder selectorNameBuilder = new StringBuilder().append(clauseName.getValue());
450 Uuid consumerSecGroupId = secRule.getRemoteGroupId();
451 if (consumerSecGroupId == null) {
452 return new SelectorName(selectorNameBuilder.toString());
455 // we cannot use name of security group in selector, because name can be changed
456 // therefore name is used only in debug mode
457 if (NeutronMapperModule.isDebugEnabled()) {
458 Optional<SecurityGroup> potentialConsumerSecGroup =
459 SecurityGroupUtils.findSecurityGroup(secRule.getRemoteGroupId(), neutron.getSecurityGroups());
460 if (!potentialConsumerSecGroup.isPresent()) {
461 LOG.error("Neutron Security Group with UUID {} does not exist but it is in {}",
462 consumerSecGroupId.getValue(), secRule);
463 throw new IllegalStateException(
464 "Neutron Security Group with UUID " + consumerSecGroupId.getValue() + " does not exist.");
467 selectorNameBuilder.append(MappingUtils.NAME_DOUBLE_DELIMETER)
468 .append(POSSIBLE_CONSUMER)
469 .append(SecurityGroupUtils.getNameOrUuid(potentialConsumerSecGroup.get()));
470 return new SelectorName(selectorNameBuilder.toString());
473 selectorNameBuilder.append(MappingUtils.NAME_DOUBLE_DELIMETER)
474 .append(POSSIBLE_CONSUMER)
475 .append(consumerSecGroupId.getValue());
476 return new SelectorName(selectorNameBuilder.toString());
479 private SelectorName getSelectorNameWithProvider(SecurityRule secRule, Neutron neutron) {
480 ClauseName clauseName = SecRuleNameDecoder.getClauseName(secRule);
481 Uuid providerSecGroupId = secRule.getSecurityGroupId();
483 // we cannot use name of security group in selector, because name can be changed
484 // therefore name is used only in debug mode
485 if (NeutronMapperModule.isDebugEnabled()) {
486 Optional<SecurityGroup> potentialProviderSecGroup =
487 SecurityGroupUtils.findSecurityGroup(secRule.getSecurityGroupId(), neutron.getSecurityGroups());
488 if (!potentialProviderSecGroup.isPresent()) {
489 LOG.error("Neutron Security Group with UUID {} does not exist but it is in {}",
490 providerSecGroupId.getValue(), secRule);
491 throw new IllegalStateException(
492 "Neutron Security Group with UUID " + providerSecGroupId.getValue() + " does not exist.");
494 String selectorName = new StringBuilder().append(clauseName.getValue())
495 .append(MappingUtils.NAME_DOUBLE_DELIMETER)
497 .append(SecurityGroupUtils.getNameOrUuid(potentialProviderSecGroup.get()))
499 return new SelectorName(selectorName);
502 String selectorName = new StringBuilder().append(clauseName.getValue())
503 .append(MappingUtils.NAME_DOUBLE_DELIMETER)
505 .append(providerSecGroupId.getValue())
507 return new SelectorName(selectorName);
511 static boolean isDirectionOpposite(Direction one, Direction two) {
512 return (one == Direction.In && two == Direction.Out) || (one == Direction.Out && two == Direction.In);
516 static boolean isOneWithinTwo(SecurityRule one, SecurityRule two) {
517 if (!isOneGroupIdWithinTwoRemoteGroupId(one, two) || !isOneGroupIdWithinTwoRemoteGroupId(two, one))
519 if (!SecRuleEntityDecoder.isEtherTypeOfOneWithinTwo(one, two))
521 if (!SecRuleEntityDecoder.isProtocolOfOneWithinTwo(one, two))
523 if (!SecRuleEntityDecoder.isPortsOfOneWithinTwo(one, two))
525 if (two.getRemoteIpPrefix() != null
526 && one.getRemoteIpPrefix() == null)
532 static boolean isOneGroupIdWithinTwoRemoteGroupId(SecurityRule one, SecurityRule two) {
533 return (two.getRemoteGroupId() == null || two.getRemoteGroupId().equals(
534 one.getSecurityGroupId()));