blob: d12d00e4012bdc1c9bd3c6e9679f02f48b8280ef [file] [log] [blame]
tomea961ff2014-10-01 12:45:15 -07001package org.onlab.onos.store.trivial.impl;
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -07002
alshabib219ebaa2014-09-22 15:41:24 -07003import static org.onlab.onos.net.flow.FlowRuleEvent.Type.RULE_REMOVED;
4import static org.slf4j.LoggerFactory.getLogger;
5
alshabiba68eb962014-09-24 20:34:13 -07006import java.util.Collection;
7import java.util.Collections;
8
tom85c612b2014-09-19 19:25:47 -07009import org.apache.felix.scr.annotations.Activate;
10import org.apache.felix.scr.annotations.Component;
11import org.apache.felix.scr.annotations.Deactivate;
12import org.apache.felix.scr.annotations.Service;
alshabiba68eb962014-09-24 20:34:13 -070013import org.onlab.onos.ApplicationId;
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -070014import org.onlab.onos.net.DeviceId;
alshabiba68eb962014-09-24 20:34:13 -070015import org.onlab.onos.net.flow.DefaultFlowRule;
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -070016import org.onlab.onos.net.flow.FlowRule;
alshabiba68eb962014-09-24 20:34:13 -070017import org.onlab.onos.net.flow.FlowRule.FlowRuleState;
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -070018import org.onlab.onos.net.flow.FlowRuleEvent;
alshabib219ebaa2014-09-22 15:41:24 -070019import org.onlab.onos.net.flow.FlowRuleEvent.Type;
tombe988312014-09-19 18:38:47 -070020import org.onlab.onos.net.flow.FlowRuleStore;
tomc78acee2014-09-24 15:16:55 -070021import org.onlab.onos.net.flow.FlowRuleStoreDelegate;
22import org.onlab.onos.store.AbstractStore;
tom85c612b2014-09-19 19:25:47 -070023import org.slf4j.Logger;
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -070024
alshabib219ebaa2014-09-22 15:41:24 -070025import com.google.common.collect.ArrayListMultimap;
26import com.google.common.collect.ImmutableSet;
27import com.google.common.collect.Multimap;
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -070028
29/**
30 * Manages inventory of flow rules using trivial in-memory implementation.
31 */
tom85c612b2014-09-19 19:25:47 -070032@Component(immediate = true)
33@Service
tomc78acee2014-09-24 15:16:55 -070034public class SimpleFlowRuleStore
35 extends AbstractStore<FlowRuleEvent, FlowRuleStoreDelegate>
36 implements FlowRuleStore {
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -070037
tom85c612b2014-09-19 19:25:47 -070038 private final Logger log = getLogger(getClass());
39
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -070040 // store entries as a pile of rules, no info about device tables
alshabiba68eb962014-09-24 20:34:13 -070041 private final Multimap<DeviceId, FlowRule> flowEntries =
42 ArrayListMultimap.<DeviceId, FlowRule>create();
43
44 private final Multimap<ApplicationId, FlowRule> flowEntriesById =
45 ArrayListMultimap.<ApplicationId, FlowRule>create();
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -070046
tom85c612b2014-09-19 19:25:47 -070047 @Activate
48 public void activate() {
49 log.info("Started");
50 }
51
52 @Deactivate
53 public void deactivate() {
54 log.info("Stopped");
55 }
56
alshabiba68eb962014-09-24 20:34:13 -070057
tombe988312014-09-19 18:38:47 -070058 @Override
alshabiba68eb962014-09-24 20:34:13 -070059 public synchronized FlowRule getFlowRule(FlowRule rule) {
60 for (FlowRule f : flowEntries.get(rule.deviceId())) {
61 if (f.equals(rule)) {
62 return f;
63 }
64 }
65 return null;
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -070066 }
67
tombe988312014-09-19 18:38:47 -070068 @Override
alshabiba68eb962014-09-24 20:34:13 -070069 public synchronized Iterable<FlowRule> getFlowEntries(DeviceId deviceId) {
70 Collection<FlowRule> rules = flowEntries.get(deviceId);
71 if (rules == null) {
72 return Collections.emptyList();
73 }
74 return ImmutableSet.copyOf(rules);
alshabib219ebaa2014-09-22 15:41:24 -070075 }
76
77 @Override
alshabiba68eb962014-09-24 20:34:13 -070078 public synchronized Iterable<FlowRule> getFlowEntriesByAppId(ApplicationId appId) {
79 Collection<FlowRule> rules = flowEntriesById.get(appId);
80 if (rules == null) {
81 return Collections.emptyList();
82 }
83 return ImmutableSet.copyOf(rules);
84 }
85
86 @Override
87 public synchronized void storeFlowRule(FlowRule rule) {
88 FlowRule f = new DefaultFlowRule(rule, FlowRuleState.PENDING_ADD);
89 DeviceId did = f.deviceId();
90 if (!flowEntries.containsEntry(did, f)) {
91 flowEntries.put(did, f);
92 flowEntriesById.put(rule.appId(), f);
93 }
94 }
95
96 @Override
97 public synchronized void deleteFlowRule(FlowRule rule) {
98 FlowRule f = new DefaultFlowRule(rule, FlowRuleState.PENDING_REMOVE);
99 DeviceId did = f.deviceId();
alshabib219ebaa2014-09-22 15:41:24 -0700100
101 /*
102 * find the rule and mark it for deletion.
103 * Ultimately a flow removed will come remove it.
104 */
alshabibbb8b1282014-09-22 17:00:18 -0700105
alshabiba68eb962014-09-24 20:34:13 -0700106 if (flowEntries.containsEntry(did, f)) {
alshabiba68eb962014-09-24 20:34:13 -0700107 flowEntries.remove(did, f);
108 flowEntries.put(did, f);
109 flowEntriesById.remove(rule.appId(), rule);
alshabib219ebaa2014-09-22 15:41:24 -0700110 }
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -0700111 }
112
tombe988312014-09-19 18:38:47 -0700113 @Override
alshabiba68eb962014-09-24 20:34:13 -0700114 public synchronized FlowRuleEvent addOrUpdateFlowRule(FlowRule rule) {
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -0700115 DeviceId did = rule.deviceId();
116
117 // check if this new rule is an update to an existing entry
alshabibba5ac482014-10-02 17:15:20 -0700118 FlowRule stored = getFlowRule(rule);
119 if (stored != null) {
alshabiba68eb962014-09-24 20:34:13 -0700120 // Multimaps support duplicates so we have to remove our rule
121 // and replace it with the current version.
122 flowEntries.remove(did, rule);
123 flowEntries.put(did, rule);
alshabibba5ac482014-10-02 17:15:20 -0700124
125 if (stored.state() == FlowRuleState.PENDING_ADD) {
126 return new FlowRuleEvent(Type.RULE_ADDED, rule);
127 }
alshabib219ebaa2014-09-22 15:41:24 -0700128 return new FlowRuleEvent(Type.RULE_UPDATED, rule);
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -0700129 }
alshabib219ebaa2014-09-22 15:41:24 -0700130
Ayaka Koshibed4e53e12014-09-18 14:24:55 -0700131 flowEntries.put(did, rule);
alshabibba5ac482014-10-02 17:15:20 -0700132 return null;
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -0700133 }
134
tombe988312014-09-19 18:38:47 -0700135 @Override
alshabiba68eb962014-09-24 20:34:13 -0700136 public synchronized FlowRuleEvent removeFlowRule(FlowRule rule) {
137 //synchronized (this) {
138 if (flowEntries.remove(rule.deviceId(), rule)) {
139 return new FlowRuleEvent(RULE_REMOVED, rule);
140 } else {
141 return null;
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -0700142 }
alshabiba68eb962014-09-24 20:34:13 -0700143 //}
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -0700144 }
Ayaka Koshibe08eabaa2014-09-17 14:59:25 -0700145}