Showing
21 changed files
with
693 additions
and
381 deletions
... | @@ -27,8 +27,7 @@ import org.onlab.onos.net.flow.TrafficSelector; | ... | @@ -27,8 +27,7 @@ import org.onlab.onos.net.flow.TrafficSelector; |
27 | import org.onlab.onos.net.flow.TrafficTreatment; | 27 | import org.onlab.onos.net.flow.TrafficTreatment; |
28 | import org.onlab.onos.net.intent.Intent; | 28 | import org.onlab.onos.net.intent.Intent; |
29 | import org.onlab.onos.net.intent.IntentService; | 29 | import org.onlab.onos.net.intent.IntentService; |
30 | -import org.onlab.onos.net.intent.PointToPointIntentWithBandwidthConstraint; | 30 | +import org.onlab.onos.net.intent.PointToPointIntent; |
31 | -import org.onlab.onos.net.resource.BandwidthResourceRequest; | ||
32 | 31 | ||
33 | import static org.onlab.onos.net.DeviceId.deviceId; | 32 | import static org.onlab.onos.net.DeviceId.deviceId; |
34 | import static org.onlab.onos.net.PortNumber.portNumber; | 33 | import static org.onlab.onos.net.PortNumber.portNumber; |
... | @@ -73,9 +72,10 @@ public class AddPointToPointIntentWithBandwidthConstraintCommand extends Connect | ... | @@ -73,9 +72,10 @@ public class AddPointToPointIntentWithBandwidthConstraintCommand extends Connect |
73 | TrafficSelector selector = buildTrafficSelector(); | 72 | TrafficSelector selector = buildTrafficSelector(); |
74 | TrafficTreatment treatment = builder().build(); | 73 | TrafficTreatment treatment = builder().build(); |
75 | 74 | ||
76 | - Intent intent = new PointToPointIntentWithBandwidthConstraint( | 75 | + // FIXME: add bandwitdh constraint |
76 | + Intent intent = new PointToPointIntent( | ||
77 | appId(), selector, treatment, | 77 | appId(), selector, treatment, |
78 | - ingress, egress, new BandwidthResourceRequest(bandwidth)); | 78 | + ingress, egress); |
79 | service.submit(intent); | 79 | service.submit(intent); |
80 | } | 80 | } |
81 | 81 | ... | ... |
... | @@ -78,6 +78,9 @@ public class IntentsListCommand extends AbstractShellCommand { | ... | @@ -78,6 +78,9 @@ public class IntentsListCommand extends AbstractShellCommand { |
78 | if (!ci.treatment().instructions().isEmpty()) { | 78 | if (!ci.treatment().instructions().isEmpty()) { |
79 | print(" treatment=%s", ci.treatment().instructions()); | 79 | print(" treatment=%s", ci.treatment().instructions()); |
80 | } | 80 | } |
81 | + if (ci.constraints() != null && !ci.constraints().isEmpty()) { | ||
82 | + print(" constraints=%s", ci.constraints()); | ||
83 | + } | ||
81 | } | 84 | } |
82 | 85 | ||
83 | if (intent instanceof PointToPointIntent) { | 86 | if (intent instanceof PointToPointIntent) { | ... | ... |
... | @@ -23,6 +23,7 @@ import org.onlab.onos.net.flow.TrafficSelector; | ... | @@ -23,6 +23,7 @@ import org.onlab.onos.net.flow.TrafficSelector; |
23 | import org.onlab.onos.net.flow.TrafficTreatment; | 23 | import org.onlab.onos.net.flow.TrafficTreatment; |
24 | 24 | ||
25 | import java.util.Collection; | 25 | import java.util.Collection; |
26 | +import java.util.List; | ||
26 | 27 | ||
27 | import static com.google.common.base.Preconditions.checkNotNull; | 28 | import static com.google.common.base.Preconditions.checkNotNull; |
28 | 29 | ||
... | @@ -40,10 +41,14 @@ public abstract class ConnectivityIntent extends Intent { | ... | @@ -40,10 +41,14 @@ public abstract class ConnectivityIntent extends Intent { |
40 | 41 | ||
41 | private final TrafficSelector selector; | 42 | private final TrafficSelector selector; |
42 | private final TrafficTreatment treatment; | 43 | private final TrafficTreatment treatment; |
44 | + private final List<Constraint> constraints; | ||
43 | 45 | ||
44 | /** | 46 | /** |
45 | * Creates a connectivity intent that matches on the specified selector | 47 | * Creates a connectivity intent that matches on the specified selector |
46 | * and applies the specified treatment. | 48 | * and applies the specified treatment. |
49 | + * <p> | ||
50 | + * Path will be chosen without any constraints. | ||
51 | + * </p> | ||
47 | * | 52 | * |
48 | * @param id intent identifier | 53 | * @param id intent identifier |
49 | * @param appId application identifier | 54 | * @param appId application identifier |
... | @@ -56,9 +61,33 @@ public abstract class ConnectivityIntent extends Intent { | ... | @@ -56,9 +61,33 @@ public abstract class ConnectivityIntent extends Intent { |
56 | Collection<NetworkResource> resources, | 61 | Collection<NetworkResource> resources, |
57 | TrafficSelector selector, | 62 | TrafficSelector selector, |
58 | TrafficTreatment treatment) { | 63 | TrafficTreatment treatment) { |
64 | + this(id, appId, resources, selector, treatment, null); | ||
65 | + } | ||
66 | + | ||
67 | + /** | ||
68 | + * Creates a connectivity intent that matches on the specified selector | ||
69 | + * and applies the specified treatment. | ||
70 | + * <p> | ||
71 | + * Path will be optimized based on the first constraint if one is given. | ||
72 | + * </p> | ||
73 | + * | ||
74 | + * @param id intent identifier | ||
75 | + * @param appId application identifier | ||
76 | + * @param resources required network resources (optional) | ||
77 | + * @param selector traffic selector | ||
78 | + * @param treatment treatment | ||
79 | + * @param constraints optional prioritized list of constraints | ||
80 | + * @throws NullPointerException if the selector or treatement is null | ||
81 | + */ | ||
82 | + protected ConnectivityIntent(IntentId id, ApplicationId appId, | ||
83 | + Collection<NetworkResource> resources, | ||
84 | + TrafficSelector selector, | ||
85 | + TrafficTreatment treatment, | ||
86 | + List<Constraint> constraints) { | ||
59 | super(id, appId, resources); | 87 | super(id, appId, resources); |
60 | this.selector = checkNotNull(selector); | 88 | this.selector = checkNotNull(selector); |
61 | this.treatment = checkNotNull(treatment); | 89 | this.treatment = checkNotNull(treatment); |
90 | + this.constraints = constraints; | ||
62 | } | 91 | } |
63 | 92 | ||
64 | /** | 93 | /** |
... | @@ -68,6 +97,7 @@ public abstract class ConnectivityIntent extends Intent { | ... | @@ -68,6 +97,7 @@ public abstract class ConnectivityIntent extends Intent { |
68 | super(); | 97 | super(); |
69 | this.selector = null; | 98 | this.selector = null; |
70 | this.treatment = null; | 99 | this.treatment = null; |
100 | + this.constraints = null; | ||
71 | } | 101 | } |
72 | 102 | ||
73 | /** | 103 | /** |
... | @@ -89,13 +119,22 @@ public abstract class ConnectivityIntent extends Intent { | ... | @@ -89,13 +119,22 @@ public abstract class ConnectivityIntent extends Intent { |
89 | } | 119 | } |
90 | 120 | ||
91 | /** | 121 | /** |
122 | + * Returns the set of connectivity constraints. | ||
123 | + * | ||
124 | + * @return list of intent constraints | ||
125 | + */ | ||
126 | + public List<Constraint> constraints() { | ||
127 | + return constraints; | ||
128 | + } | ||
129 | + | ||
130 | + /** | ||
92 | * Produces a collection of network resources from the given links. | 131 | * Produces a collection of network resources from the given links. |
93 | * | 132 | * |
94 | * @param links collection of links | 133 | * @param links collection of links |
95 | * @return collection of link resources | 134 | * @return collection of link resources |
96 | */ | 135 | */ |
97 | protected static Collection<NetworkResource> resources(Collection<Link> links) { | 136 | protected static Collection<NetworkResource> resources(Collection<Link> links) { |
98 | - return ImmutableSet.<NetworkResource>copyOf(links); | 137 | + return ImmutableSet.<NetworkResource>copyOf((Iterable<? extends NetworkResource>) links); |
99 | } | 138 | } |
100 | 139 | ||
101 | } | 140 | } | ... | ... |
1 | +/* | ||
2 | + * Copyright 2014 Open Networking Laboratory | ||
3 | + * | ||
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
5 | + * you may not use this file except in compliance with the License. | ||
6 | + * You may obtain a copy of the License at | ||
7 | + * | ||
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
9 | + * | ||
10 | + * Unless required by applicable law or agreed to in writing, software | ||
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
13 | + * See the License for the specific language governing permissions and | ||
14 | + * limitations under the License. | ||
15 | + */ | ||
16 | +package org.onlab.onos.net.intent; | ||
17 | + | ||
18 | +import org.onlab.onos.net.Link; | ||
19 | +import org.onlab.onos.net.Path; | ||
20 | +import org.onlab.onos.net.resource.LinkResourceService; | ||
21 | + | ||
22 | +/** | ||
23 | + * Representation of a connectivity constraint capable of evaluating a link | ||
24 | + * and determining the cost of traversing that link in the context of this | ||
25 | + * constraint. | ||
26 | + */ | ||
27 | +public interface Constraint { | ||
28 | + | ||
29 | + // TODO: Consider separating cost vs viability. | ||
30 | + | ||
31 | + /** | ||
32 | + * Evaluates the specified link and provides the cost for its traversal. | ||
33 | + * | ||
34 | + * @param link link to be evaluated | ||
35 | + * @param resourceService resource service for validating availability of | ||
36 | + * link resources | ||
37 | + * @return cost of link traversal | ||
38 | + */ | ||
39 | + double cost(Link link, LinkResourceService resourceService); | ||
40 | + | ||
41 | + /** | ||
42 | + * Validates that the specified path satisfies the constraint. | ||
43 | + * | ||
44 | + * @param path path to be validated | ||
45 | + * @param resourceService resource service for validating availability of | ||
46 | + * link resources | ||
47 | + * @return cost of link traversal | ||
48 | + */ | ||
49 | + boolean validate(Path path, LinkResourceService resourceService); | ||
50 | + | ||
51 | +} |
... | @@ -21,6 +21,8 @@ import org.onlab.onos.net.HostId; | ... | @@ -21,6 +21,8 @@ import org.onlab.onos.net.HostId; |
21 | import org.onlab.onos.net.flow.TrafficSelector; | 21 | import org.onlab.onos.net.flow.TrafficSelector; |
22 | import org.onlab.onos.net.flow.TrafficTreatment; | 22 | import org.onlab.onos.net.flow.TrafficTreatment; |
23 | 23 | ||
24 | +import java.util.List; | ||
25 | + | ||
24 | import static com.google.common.base.Preconditions.checkNotNull; | 26 | import static com.google.common.base.Preconditions.checkNotNull; |
25 | 27 | ||
26 | /** | 28 | /** |
... | @@ -44,11 +46,30 @@ public final class HostToHostIntent extends ConnectivityIntent { | ... | @@ -44,11 +46,30 @@ public final class HostToHostIntent extends ConnectivityIntent { |
44 | public HostToHostIntent(ApplicationId appId, HostId one, HostId two, | 46 | public HostToHostIntent(ApplicationId appId, HostId one, HostId two, |
45 | TrafficSelector selector, | 47 | TrafficSelector selector, |
46 | TrafficTreatment treatment) { | 48 | TrafficTreatment treatment) { |
49 | + this(appId, one, two, selector, treatment, null); | ||
50 | + } | ||
51 | + | ||
52 | + /** | ||
53 | + * Creates a new host-to-host intent with the supplied host pair. | ||
54 | + * | ||
55 | + * @param appId application identifier | ||
56 | + * @param one first host | ||
57 | + * @param two second host | ||
58 | + * @param selector action | ||
59 | + * @param treatment ingress port | ||
60 | + * @param constraints optional prioritized list of path selection constraints | ||
61 | + * @throws NullPointerException if {@code one} or {@code two} is null. | ||
62 | + */ | ||
63 | + public HostToHostIntent(ApplicationId appId, HostId one, HostId two, | ||
64 | + TrafficSelector selector, | ||
65 | + TrafficTreatment treatment, | ||
66 | + List<Constraint> constraints) { | ||
47 | super(id(HostToHostIntent.class, min(one, two), max(one, two), | 67 | super(id(HostToHostIntent.class, min(one, two), max(one, two), |
48 | - selector, treatment), | 68 | + selector, treatment, constraints), |
49 | - appId, null, selector, treatment); | 69 | + appId, null, selector, treatment, constraints); |
50 | this.one = checkNotNull(one); | 70 | this.one = checkNotNull(one); |
51 | this.two = checkNotNull(two); | 71 | this.two = checkNotNull(two); |
72 | + | ||
52 | } | 73 | } |
53 | 74 | ||
54 | private static HostId min(HostId one, HostId two) { | 75 | private static HostId min(HostId one, HostId two) { | ... | ... |
... | @@ -51,6 +51,15 @@ public final class IntentId implements BatchOperationTarget { | ... | @@ -51,6 +51,15 @@ public final class IntentId implements BatchOperationTarget { |
51 | this.fingerprint = fingerprint; | 51 | this.fingerprint = fingerprint; |
52 | } | 52 | } |
53 | 53 | ||
54 | + /** | ||
55 | + * Returns the backing fingerprint. | ||
56 | + * | ||
57 | + * @return the fingerprint | ||
58 | + */ | ||
59 | + public long fingerprint() { | ||
60 | + return fingerprint; | ||
61 | + } | ||
62 | + | ||
54 | @Override | 63 | @Override |
55 | public int hashCode() { | 64 | public int hashCode() { |
56 | return (int) (fingerprint ^ (fingerprint >>> 32)); | 65 | return (int) (fingerprint ^ (fingerprint >>> 32)); | ... | ... |
... | @@ -15,16 +15,11 @@ | ... | @@ -15,16 +15,11 @@ |
15 | */ | 15 | */ |
16 | package org.onlab.onos.net.intent; | 16 | package org.onlab.onos.net.intent; |
17 | 17 | ||
18 | -import java.util.List; | ||
19 | - | ||
20 | import com.google.common.base.MoreObjects; | 18 | import com.google.common.base.MoreObjects; |
21 | -import com.google.common.collect.ImmutableList; | ||
22 | - | ||
23 | import org.onlab.onos.core.ApplicationId; | 19 | import org.onlab.onos.core.ApplicationId; |
24 | import org.onlab.onos.net.Path; | 20 | import org.onlab.onos.net.Path; |
25 | import org.onlab.onos.net.flow.TrafficSelector; | 21 | import org.onlab.onos.net.flow.TrafficSelector; |
26 | import org.onlab.onos.net.flow.TrafficTreatment; | 22 | import org.onlab.onos.net.flow.TrafficTreatment; |
27 | -import org.onlab.onos.net.resource.LinkResourceRequest; | ||
28 | 23 | ||
29 | /** | 24 | /** |
30 | * Abstraction of explicitly path specified connectivity intent. | 25 | * Abstraction of explicitly path specified connectivity intent. |
... | @@ -32,7 +27,6 @@ import org.onlab.onos.net.resource.LinkResourceRequest; | ... | @@ -32,7 +27,6 @@ import org.onlab.onos.net.resource.LinkResourceRequest; |
32 | public class PathIntent extends ConnectivityIntent { | 27 | public class PathIntent extends ConnectivityIntent { |
33 | 28 | ||
34 | private final Path path; | 29 | private final Path path; |
35 | - private final List<LinkResourceRequest> resourceRequests; | ||
36 | 30 | ||
37 | /** | 31 | /** |
38 | * Creates a new point-to-point intent with the supplied ingress/egress | 32 | * Creates a new point-to-point intent with the supplied ingress/egress |
... | @@ -42,15 +36,13 @@ public class PathIntent extends ConnectivityIntent { | ... | @@ -42,15 +36,13 @@ public class PathIntent extends ConnectivityIntent { |
42 | * @param selector traffic selector | 36 | * @param selector traffic selector |
43 | * @param treatment treatment | 37 | * @param treatment treatment |
44 | * @param path traversed links | 38 | * @param path traversed links |
45 | - * @param resourceRequests link resource request | ||
46 | * @throws NullPointerException {@code path} is null | 39 | * @throws NullPointerException {@code path} is null |
47 | */ | 40 | */ |
48 | public PathIntent(ApplicationId appId, TrafficSelector selector, | 41 | public PathIntent(ApplicationId appId, TrafficSelector selector, |
49 | - TrafficTreatment treatment, Path path, LinkResourceRequest[] resourceRequests) { | 42 | + TrafficTreatment treatment, Path path) { |
50 | super(id(PathIntent.class, selector, treatment, path), appId, | 43 | super(id(PathIntent.class, selector, treatment, path), appId, |
51 | resources(path.links()), selector, treatment); | 44 | resources(path.links()), selector, treatment); |
52 | this.path = path; | 45 | this.path = path; |
53 | - this.resourceRequests = ImmutableList.copyOf(resourceRequests); | ||
54 | } | 46 | } |
55 | 47 | ||
56 | /** | 48 | /** |
... | @@ -59,7 +51,6 @@ public class PathIntent extends ConnectivityIntent { | ... | @@ -59,7 +51,6 @@ public class PathIntent extends ConnectivityIntent { |
59 | protected PathIntent() { | 51 | protected PathIntent() { |
60 | super(); | 52 | super(); |
61 | this.path = null; | 53 | this.path = null; |
62 | - this.resourceRequests = ImmutableList.of(); | ||
63 | } | 54 | } |
64 | 55 | ||
65 | /** | 56 | /** |
... | @@ -76,10 +67,6 @@ public class PathIntent extends ConnectivityIntent { | ... | @@ -76,10 +67,6 @@ public class PathIntent extends ConnectivityIntent { |
76 | return true; | 67 | return true; |
77 | } | 68 | } |
78 | 69 | ||
79 | - // TODO: consider changing return type | ||
80 | - public LinkResourceRequest[] resourceRequests() { | ||
81 | - return resourceRequests.toArray(new LinkResourceRequest[resourceRequests.size()]); | ||
82 | - } | ||
83 | 70 | ||
84 | @Override | 71 | @Override |
85 | public String toString() { | 72 | public String toString() { | ... | ... |
... | @@ -16,10 +16,15 @@ | ... | @@ -16,10 +16,15 @@ |
16 | package org.onlab.onos.net.intent; | 16 | package org.onlab.onos.net.intent; |
17 | 17 | ||
18 | import com.google.common.base.MoreObjects; | 18 | import com.google.common.base.MoreObjects; |
19 | +import com.google.common.collect.ImmutableList; | ||
19 | import org.onlab.onos.core.ApplicationId; | 20 | import org.onlab.onos.core.ApplicationId; |
20 | import org.onlab.onos.net.ConnectPoint; | 21 | import org.onlab.onos.net.ConnectPoint; |
22 | +import org.onlab.onos.net.Link; | ||
21 | import org.onlab.onos.net.flow.TrafficSelector; | 23 | import org.onlab.onos.net.flow.TrafficSelector; |
22 | import org.onlab.onos.net.flow.TrafficTreatment; | 24 | import org.onlab.onos.net.flow.TrafficTreatment; |
25 | +import org.onlab.onos.net.intent.constraint.LinkTypeConstraint; | ||
26 | + | ||
27 | +import java.util.List; | ||
23 | 28 | ||
24 | import static com.google.common.base.Preconditions.checkNotNull; | 29 | import static com.google.common.base.Preconditions.checkNotNull; |
25 | 30 | ||
... | @@ -33,7 +38,7 @@ public class PointToPointIntent extends ConnectivityIntent { | ... | @@ -33,7 +38,7 @@ public class PointToPointIntent extends ConnectivityIntent { |
33 | 38 | ||
34 | /** | 39 | /** |
35 | * Creates a new point-to-point intent with the supplied ingress/egress | 40 | * Creates a new point-to-point intent with the supplied ingress/egress |
36 | - * ports. | 41 | + * ports and with built-in link type constraint to avoid optical links. |
37 | * | 42 | * |
38 | * @param appId application identifier | 43 | * @param appId application identifier |
39 | * @param selector traffic selector | 44 | * @param selector traffic selector |
... | @@ -46,8 +51,30 @@ public class PointToPointIntent extends ConnectivityIntent { | ... | @@ -46,8 +51,30 @@ public class PointToPointIntent extends ConnectivityIntent { |
46 | TrafficTreatment treatment, | 51 | TrafficTreatment treatment, |
47 | ConnectPoint ingressPoint, | 52 | ConnectPoint ingressPoint, |
48 | ConnectPoint egressPoint) { | 53 | ConnectPoint egressPoint) { |
49 | - super(id(PointToPointIntent.class, selector, treatment, ingressPoint, egressPoint), | 54 | + this(appId, selector, treatment, ingressPoint, egressPoint, |
50 | - appId, null, selector, treatment); | 55 | + ImmutableList.of(new LinkTypeConstraint(false, Link.Type.OPTICAL))); |
56 | + } | ||
57 | + | ||
58 | + /** | ||
59 | + * Creates a new point-to-point intent with the supplied ingress/egress | ||
60 | + * ports and constraints. | ||
61 | + * | ||
62 | + * @param appId application identifier | ||
63 | + * @param selector traffic selector | ||
64 | + * @param treatment treatment | ||
65 | + * @param ingressPoint ingress port | ||
66 | + * @param egressPoint egress port | ||
67 | + * @param constraints optional list of constraints | ||
68 | + * @throws NullPointerException if {@code ingressPoint} or {@code egressPoints} is null. | ||
69 | + */ | ||
70 | + public PointToPointIntent(ApplicationId appId, TrafficSelector selector, | ||
71 | + TrafficTreatment treatment, | ||
72 | + ConnectPoint ingressPoint, | ||
73 | + ConnectPoint egressPoint, | ||
74 | + List<Constraint> constraints) { | ||
75 | + super(id(PointToPointIntent.class, selector, treatment, | ||
76 | + ingressPoint, egressPoint, constraints), | ||
77 | + appId, null, selector, treatment, constraints); | ||
51 | this.ingressPoint = checkNotNull(ingressPoint); | 78 | this.ingressPoint = checkNotNull(ingressPoint); |
52 | this.egressPoint = checkNotNull(egressPoint); | 79 | this.egressPoint = checkNotNull(egressPoint); |
53 | } | 80 | } |
... | @@ -89,6 +116,7 @@ public class PointToPointIntent extends ConnectivityIntent { | ... | @@ -89,6 +116,7 @@ public class PointToPointIntent extends ConnectivityIntent { |
89 | .add("treatment", treatment()) | 116 | .add("treatment", treatment()) |
90 | .add("ingress", ingressPoint) | 117 | .add("ingress", ingressPoint) |
91 | .add("egress", egressPoint) | 118 | .add("egress", egressPoint) |
119 | + .add("constraints", constraints()) | ||
92 | .toString(); | 120 | .toString(); |
93 | } | 121 | } |
94 | 122 | ... | ... |
1 | -/* | ||
2 | - * Licensed to the Apache Software Foundation (ASF) under one | ||
3 | - * or more contributor license agreements. See the NOTICE file | ||
4 | - * distributed with this work for additional information | ||
5 | - * regarding copyright ownership. The ASF licenses this file | ||
6 | - * to you under the Apache License, Version 2.0 (the | ||
7 | - * "License"); you may not use this file except in compliance | ||
8 | - * with the License. You may obtain a copy of the License at | ||
9 | - * | ||
10 | - * http://www.apache.org/licenses/LICENSE-2.0 | ||
11 | - * | ||
12 | - * Unless required by applicable law or agreed to in writing, | ||
13 | - * software distributed under the License is distributed on an | ||
14 | - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY | ||
15 | - * KIND, either express or implied. See the License for the | ||
16 | - * specific language governing permissions and limitations | ||
17 | - * under the License. | ||
18 | - */ | ||
19 | -package org.onlab.onos.net.intent; | ||
20 | - | ||
21 | -import org.onlab.onos.core.ApplicationId; | ||
22 | -import org.onlab.onos.net.ConnectPoint; | ||
23 | -import org.onlab.onos.net.flow.TrafficSelector; | ||
24 | -import org.onlab.onos.net.flow.TrafficTreatment; | ||
25 | -import org.onlab.onos.net.resource.BandwidthResourceRequest; | ||
26 | - | ||
27 | -import com.google.common.base.MoreObjects; | ||
28 | - | ||
29 | -import static com.google.common.base.Preconditions.checkNotNull; | ||
30 | - | ||
31 | -/** | ||
32 | - * Abstraction of point-to-point connectivity. | ||
33 | - */ | ||
34 | -public class PointToPointIntentWithBandwidthConstraint extends ConnectivityIntent { | ||
35 | - | ||
36 | - private final ConnectPoint ingressPoint; | ||
37 | - private final ConnectPoint egressPoint; | ||
38 | - private final BandwidthResourceRequest bandwidthResourceRequest; | ||
39 | - | ||
40 | - /** | ||
41 | - * Creates a new point-to-point intent with the supplied ingress/egress | ||
42 | - * ports. | ||
43 | - * | ||
44 | - * @param appId application identifier | ||
45 | - * @param selector traffic selector | ||
46 | - * @param treatment treatment | ||
47 | - * @param ingressPoint ingress port | ||
48 | - * @param egressPoint egress port | ||
49 | - * @param bandwidthResourceRequest bandwidth resource request | ||
50 | - * @throws NullPointerException if {@code ingressPoint} or {@code egressPoints} is null. | ||
51 | - */ | ||
52 | - public PointToPointIntentWithBandwidthConstraint(ApplicationId appId, TrafficSelector selector, | ||
53 | - TrafficTreatment treatment, | ||
54 | - ConnectPoint ingressPoint, | ||
55 | - ConnectPoint egressPoint, | ||
56 | - BandwidthResourceRequest bandwidthResourceRequest) { | ||
57 | - super(id(PointToPointIntentWithBandwidthConstraint.class, selector, | ||
58 | - treatment, ingressPoint, egressPoint, bandwidthResourceRequest.bandwidth()), | ||
59 | - appId, null, selector, treatment); | ||
60 | - this.ingressPoint = checkNotNull(ingressPoint); | ||
61 | - this.egressPoint = checkNotNull(egressPoint); | ||
62 | - this.bandwidthResourceRequest = bandwidthResourceRequest; | ||
63 | - } | ||
64 | - | ||
65 | - /** | ||
66 | - * Constructor for serializer. | ||
67 | - */ | ||
68 | - protected PointToPointIntentWithBandwidthConstraint() { | ||
69 | - super(); | ||
70 | - this.ingressPoint = null; | ||
71 | - this.egressPoint = null; | ||
72 | - bandwidthResourceRequest = new BandwidthResourceRequest(0.0); | ||
73 | - } | ||
74 | - | ||
75 | - /** | ||
76 | - * Returns the port on which the ingress traffic should be connected to | ||
77 | - * the egress. | ||
78 | - * | ||
79 | - * @return ingress port | ||
80 | - */ | ||
81 | - public ConnectPoint ingressPoint() { | ||
82 | - return ingressPoint; | ||
83 | - } | ||
84 | - | ||
85 | - /** | ||
86 | - * Returns the port on which the traffic should egress. | ||
87 | - * | ||
88 | - * @return egress port | ||
89 | - */ | ||
90 | - public ConnectPoint egressPoint() { | ||
91 | - return egressPoint; | ||
92 | - } | ||
93 | - | ||
94 | - public BandwidthResourceRequest bandwidthRequest() { | ||
95 | - return this.bandwidthResourceRequest; | ||
96 | - } | ||
97 | - | ||
98 | - @Override | ||
99 | - public String toString() { | ||
100 | - return MoreObjects.toStringHelper(getClass()) | ||
101 | - .add("id", id()) | ||
102 | - .add("appId", appId()) | ||
103 | - .add("selector", selector()) | ||
104 | - .add("treatment", treatment()) | ||
105 | - .add("ingress", ingressPoint) | ||
106 | - .add("egress", egressPoint) | ||
107 | - .add("bandwidth", bandwidthResourceRequest.bandwidth().toString()) | ||
108 | - .toString(); | ||
109 | - } | ||
110 | - | ||
111 | -} |
1 | +/* | ||
2 | + * Copyright 2014 Open Networking Laboratory | ||
3 | + * | ||
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
5 | + * you may not use this file except in compliance with the License. | ||
6 | + * You may obtain a copy of the License at | ||
7 | + * | ||
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
9 | + * | ||
10 | + * Unless required by applicable law or agreed to in writing, software | ||
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
13 | + * See the License for the specific language governing permissions and | ||
14 | + * limitations under the License. | ||
15 | + */ | ||
16 | +package org.onlab.onos.net.intent.constraint; | ||
17 | + | ||
18 | +import org.onlab.onos.net.Link; | ||
19 | +import org.onlab.onos.net.resource.Bandwidth; | ||
20 | +import org.onlab.onos.net.resource.BandwidthResourceRequest; | ||
21 | +import org.onlab.onos.net.resource.LinkResourceService; | ||
22 | +import org.onlab.onos.net.resource.ResourceRequest; | ||
23 | +import org.onlab.onos.net.resource.ResourceType; | ||
24 | + | ||
25 | +import java.util.Objects; | ||
26 | + | ||
27 | +import static com.google.common.base.MoreObjects.toStringHelper; | ||
28 | +import static com.google.common.base.Preconditions.checkNotNull; | ||
29 | + | ||
30 | +/** | ||
31 | + * Constraint that evaluates links based on available bandwidths. | ||
32 | + */ | ||
33 | +public class BandwidthConstraint extends BooleanConstraint { | ||
34 | + | ||
35 | + private final Bandwidth bandwidth; | ||
36 | + | ||
37 | + /** | ||
38 | + * Creates a new bandwidth constraint. | ||
39 | + * | ||
40 | + * @param bandwidth required bandwidth | ||
41 | + */ | ||
42 | + public BandwidthConstraint(Bandwidth bandwidth) { | ||
43 | + this.bandwidth = checkNotNull(bandwidth, "Bandwidth cannot be null"); | ||
44 | + } | ||
45 | + | ||
46 | + @Override | ||
47 | + public boolean isValid(Link link, LinkResourceService resourceService) { | ||
48 | + for (ResourceRequest request : resourceService.getAvailableResources(link)) { | ||
49 | + if (request.type() == ResourceType.BANDWIDTH) { | ||
50 | + BandwidthResourceRequest brr = (BandwidthResourceRequest) request; | ||
51 | + if (brr.bandwidth().toDouble() >= bandwidth.toDouble()) { | ||
52 | + return true; | ||
53 | + } | ||
54 | + } | ||
55 | + } | ||
56 | + return false; | ||
57 | + } | ||
58 | + | ||
59 | + /** | ||
60 | + * Returns the bandwidth required by this constraint. | ||
61 | + * | ||
62 | + * @return required bandwidth | ||
63 | + */ | ||
64 | + public Bandwidth bandwidth() { | ||
65 | + return bandwidth; | ||
66 | + } | ||
67 | + | ||
68 | + @Override | ||
69 | + public int hashCode() { | ||
70 | + return Objects.hash(bandwidth); | ||
71 | + } | ||
72 | + | ||
73 | + @Override | ||
74 | + public boolean equals(Object obj) { | ||
75 | + if (this == obj) { | ||
76 | + return true; | ||
77 | + } | ||
78 | + if (obj == null || getClass() != obj.getClass()) { | ||
79 | + return false; | ||
80 | + } | ||
81 | + final BandwidthConstraint other = (BandwidthConstraint) obj; | ||
82 | + return Objects.equals(this.bandwidth, other.bandwidth); | ||
83 | + } | ||
84 | + | ||
85 | + @Override | ||
86 | + public String toString() { | ||
87 | + return toStringHelper(this).add("bandwidth", bandwidth).toString(); | ||
88 | + } | ||
89 | +} |
1 | +/* | ||
2 | + * Copyright 2014 Open Networking Laboratory | ||
3 | + * | ||
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
5 | + * you may not use this file except in compliance with the License. | ||
6 | + * You may obtain a copy of the License at | ||
7 | + * | ||
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
9 | + * | ||
10 | + * Unless required by applicable law or agreed to in writing, software | ||
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
13 | + * See the License for the specific language governing permissions and | ||
14 | + * limitations under the License. | ||
15 | + */ | ||
16 | +package org.onlab.onos.net.intent.constraint; | ||
17 | + | ||
18 | +import org.onlab.onos.net.Link; | ||
19 | +import org.onlab.onos.net.Path; | ||
20 | +import org.onlab.onos.net.intent.Constraint; | ||
21 | +import org.onlab.onos.net.resource.LinkResourceService; | ||
22 | + | ||
23 | +/** | ||
24 | + * Abstract base class for various constraints that evaluate link viability | ||
25 | + * in a yes/no fashion. | ||
26 | + */ | ||
27 | +public abstract class BooleanConstraint implements Constraint { | ||
28 | + | ||
29 | + /** | ||
30 | + * Returns true if the specified link satisfies the constraint. | ||
31 | + * | ||
32 | + * @param link link to be validated | ||
33 | + * @param resourceService resource service for checking available link resources | ||
34 | + * @return true if link is viable | ||
35 | + */ | ||
36 | + public abstract boolean isValid(Link link, LinkResourceService resourceService); | ||
37 | + | ||
38 | + @Override | ||
39 | + public double cost(Link link, LinkResourceService resourceService) { | ||
40 | + return isValid(link, resourceService) ? +1 : -1; | ||
41 | + } | ||
42 | + | ||
43 | + @Override | ||
44 | + public boolean validate(Path path, LinkResourceService resourceService) { | ||
45 | + for (Link link : path.links()) { | ||
46 | + if (isValid(link, resourceService)) { | ||
47 | + return false; | ||
48 | + } | ||
49 | + } | ||
50 | + return true; | ||
51 | + } | ||
52 | + | ||
53 | +} |
1 | +/* | ||
2 | + * Copyright 2014 Open Networking Laboratory | ||
3 | + * | ||
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
5 | + * you may not use this file except in compliance with the License. | ||
6 | + * You may obtain a copy of the License at | ||
7 | + * | ||
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
9 | + * | ||
10 | + * Unless required by applicable law or agreed to in writing, software | ||
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
13 | + * See the License for the specific language governing permissions and | ||
14 | + * limitations under the License. | ||
15 | + */ | ||
16 | +package org.onlab.onos.net.intent.constraint; | ||
17 | + | ||
18 | +import org.onlab.onos.net.Link; | ||
19 | +import org.onlab.onos.net.resource.Lambda; | ||
20 | +import org.onlab.onos.net.resource.LinkResourceService; | ||
21 | +import org.onlab.onos.net.resource.ResourceRequest; | ||
22 | +import org.onlab.onos.net.resource.ResourceType; | ||
23 | + | ||
24 | +import java.util.Objects; | ||
25 | + | ||
26 | +import static com.google.common.base.MoreObjects.toStringHelper; | ||
27 | + | ||
28 | +/** | ||
29 | + * Constraint that evaluates links based on available lambda. | ||
30 | + */ | ||
31 | +public class LambdaConstraint extends BooleanConstraint { | ||
32 | + | ||
33 | + private final Lambda lambda; | ||
34 | + | ||
35 | + /** | ||
36 | + * Creates a new optical lambda constraint. | ||
37 | + * | ||
38 | + * @param lambda optional lambda to indicate a specific lambda | ||
39 | + */ | ||
40 | + public LambdaConstraint(Lambda lambda) { | ||
41 | + this.lambda = lambda; | ||
42 | + } | ||
43 | + | ||
44 | + @Override | ||
45 | + public boolean isValid(Link link, LinkResourceService resourceService) { | ||
46 | + for (ResourceRequest request : resourceService.getAvailableResources(link)) { | ||
47 | + if (request.type() == ResourceType.LAMBDA) { | ||
48 | + return true; | ||
49 | + } | ||
50 | + } | ||
51 | + return false; | ||
52 | + } | ||
53 | + | ||
54 | + /** | ||
55 | + * Returns the lambda required by this constraint. | ||
56 | + * | ||
57 | + * @return required lambda | ||
58 | + */ | ||
59 | + public Lambda lambda() { | ||
60 | + return lambda; | ||
61 | + } | ||
62 | + | ||
63 | + @Override | ||
64 | + public int hashCode() { | ||
65 | + return Objects.hash(lambda); | ||
66 | + } | ||
67 | + | ||
68 | + @Override | ||
69 | + public boolean equals(Object obj) { | ||
70 | + if (this == obj) { | ||
71 | + return true; | ||
72 | + } | ||
73 | + if (obj == null || getClass() != obj.getClass()) { | ||
74 | + return false; | ||
75 | + } | ||
76 | + final LambdaConstraint other = (LambdaConstraint) obj; | ||
77 | + return Objects.equals(this.lambda, other.lambda); | ||
78 | + } | ||
79 | + | ||
80 | + @Override | ||
81 | + public String toString() { | ||
82 | + return toStringHelper(this).add("lambda", lambda).toString(); | ||
83 | + } | ||
84 | +} |
1 | +/* | ||
2 | + * Copyright 2014 Open Networking Laboratory | ||
3 | + * | ||
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
5 | + * you may not use this file except in compliance with the License. | ||
6 | + * You may obtain a copy of the License at | ||
7 | + * | ||
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
9 | + * | ||
10 | + * Unless required by applicable law or agreed to in writing, software | ||
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
13 | + * See the License for the specific language governing permissions and | ||
14 | + * limitations under the License. | ||
15 | + */ | ||
16 | +package org.onlab.onos.net.intent.constraint; | ||
17 | + | ||
18 | +import com.google.common.collect.ImmutableSet; | ||
19 | +import org.onlab.onos.net.Link; | ||
20 | +import org.onlab.onos.net.resource.LinkResourceService; | ||
21 | + | ||
22 | +import java.util.Objects; | ||
23 | +import java.util.Set; | ||
24 | + | ||
25 | +import static com.google.common.base.MoreObjects.toStringHelper; | ||
26 | +import static com.google.common.base.Preconditions.checkArgument; | ||
27 | +import static com.google.common.base.Preconditions.checkNotNull; | ||
28 | + | ||
29 | +/** | ||
30 | + * Constraint that evaluates links based on their type. | ||
31 | + */ | ||
32 | +public class LinkTypeConstraint extends BooleanConstraint { | ||
33 | + | ||
34 | + private final Set<Link.Type> types; | ||
35 | + private final boolean isInclusive; | ||
36 | + | ||
37 | + /** | ||
38 | + * Creates a new constraint for requesting connectivity using or avoiding | ||
39 | + * the specified link types. | ||
40 | + * | ||
41 | + * @param inclusive indicates whether the given link types are to be | ||
42 | + * permitted or avoided | ||
43 | + * @param types link types | ||
44 | + */ | ||
45 | + public LinkTypeConstraint(boolean inclusive, Link.Type... types) { | ||
46 | + checkNotNull(types, "Link types cannot be null"); | ||
47 | + checkArgument(types.length > 0, "There must be more than one type"); | ||
48 | + this.types = ImmutableSet.copyOf(types); | ||
49 | + this.isInclusive = inclusive; | ||
50 | + } | ||
51 | + | ||
52 | + @Override | ||
53 | + public boolean isValid(Link link, LinkResourceService resourceService) { | ||
54 | + boolean contains = types.contains(link.type()); | ||
55 | + return isInclusive ? contains : !contains; | ||
56 | + } | ||
57 | + | ||
58 | + /** | ||
59 | + * Returns the set of link types. | ||
60 | + * | ||
61 | + * @return set of link types | ||
62 | + */ | ||
63 | + public Set<Link.Type> types() { | ||
64 | + return types; | ||
65 | + } | ||
66 | + | ||
67 | + /** | ||
68 | + * Indicates if the constraint is inclusive or exclusive. | ||
69 | + * | ||
70 | + * @return true if inclusive | ||
71 | + */ | ||
72 | + public boolean isInclusive() { | ||
73 | + return isInclusive; | ||
74 | + } | ||
75 | + | ||
76 | + @Override | ||
77 | + public int hashCode() { | ||
78 | + return Objects.hash(types, isInclusive); | ||
79 | + } | ||
80 | + | ||
81 | + @Override | ||
82 | + public boolean equals(Object obj) { | ||
83 | + if (this == obj) { | ||
84 | + return true; | ||
85 | + } | ||
86 | + if (obj == null || getClass() != obj.getClass()) { | ||
87 | + return false; | ||
88 | + } | ||
89 | + final LinkTypeConstraint other = (LinkTypeConstraint) obj; | ||
90 | + return Objects.equals(this.types, other.types) && Objects.equals(this.isInclusive, other.isInclusive); | ||
91 | + } | ||
92 | + | ||
93 | + @Override | ||
94 | + public String toString() { | ||
95 | + return toStringHelper(this) | ||
96 | + .add("inclusive", isInclusive) | ||
97 | + .add("types", types) | ||
98 | + .toString(); | ||
99 | + } | ||
100 | +} |
... | @@ -20,9 +20,12 @@ import java.util.HashSet; | ... | @@ -20,9 +20,12 @@ import java.util.HashSet; |
20 | import java.util.Set; | 20 | import java.util.Set; |
21 | 21 | ||
22 | import org.onlab.onos.net.Link; | 22 | import org.onlab.onos.net.Link; |
23 | +import org.onlab.onos.net.intent.Constraint; | ||
23 | import org.onlab.onos.net.intent.IntentId; | 24 | import org.onlab.onos.net.intent.IntentId; |
24 | 25 | ||
25 | import com.google.common.collect.ImmutableSet; | 26 | import com.google.common.collect.ImmutableSet; |
27 | +import org.onlab.onos.net.intent.constraint.BandwidthConstraint; | ||
28 | +import org.onlab.onos.net.intent.constraint.LambdaConstraint; | ||
26 | 29 | ||
27 | /** | 30 | /** |
28 | * Implementation of {@link LinkResourceRequest}. | 31 | * Implementation of {@link LinkResourceRequest}. |
... | @@ -125,6 +128,18 @@ public final class DefaultLinkResourceRequest implements LinkResourceRequest { | ... | @@ -125,6 +128,18 @@ public final class DefaultLinkResourceRequest implements LinkResourceRequest { |
125 | return this; | 128 | return this; |
126 | } | 129 | } |
127 | 130 | ||
131 | + @Override | ||
132 | + public LinkResourceRequest.Builder addConstraint(Constraint constraint) { | ||
133 | + if (constraint instanceof LambdaConstraint) { | ||
134 | + return addLambdaRequest(); | ||
135 | + } else if (constraint instanceof BandwidthConstraint) { | ||
136 | + BandwidthConstraint bw = (BandwidthConstraint) constraint; | ||
137 | + return addBandwidthRequest(bw.bandwidth().toDouble()); | ||
138 | + } | ||
139 | + return this; | ||
140 | + } | ||
141 | + | ||
142 | + | ||
128 | /** | 143 | /** |
129 | * Returns link resource request. | 144 | * Returns link resource request. |
130 | * | 145 | * | ... | ... |
... | @@ -19,6 +19,7 @@ import java.util.Collection; | ... | @@ -19,6 +19,7 @@ import java.util.Collection; |
19 | import java.util.Set; | 19 | import java.util.Set; |
20 | 20 | ||
21 | import org.onlab.onos.net.Link; | 21 | import org.onlab.onos.net.Link; |
22 | +import org.onlab.onos.net.intent.Constraint; | ||
22 | import org.onlab.onos.net.intent.IntentId; | 23 | import org.onlab.onos.net.intent.IntentId; |
23 | 24 | ||
24 | /** | 25 | /** |
... | @@ -67,6 +68,14 @@ public interface LinkResourceRequest extends ResourceRequest { | ... | @@ -67,6 +68,14 @@ public interface LinkResourceRequest extends ResourceRequest { |
67 | public Builder addBandwidthRequest(double bandwidth); | 68 | public Builder addBandwidthRequest(double bandwidth); |
68 | 69 | ||
69 | /** | 70 | /** |
71 | + * Adds the resources required for a constraint. | ||
72 | + * | ||
73 | + * @param constraint the constraint | ||
74 | + * @return self | ||
75 | + */ | ||
76 | + public Builder addConstraint(Constraint constraint); | ||
77 | + | ||
78 | + /** | ||
70 | * Returns link resource request. | 79 | * Returns link resource request. |
71 | * | 80 | * |
72 | * @return link resource request | 81 | * @return link resource request | ... | ... |
... | @@ -18,7 +18,6 @@ package org.onlab.onos.net.intent; | ... | @@ -18,7 +18,6 @@ package org.onlab.onos.net.intent; |
18 | import org.junit.Test; | 18 | import org.junit.Test; |
19 | import org.onlab.onos.net.NetTestTools; | 19 | import org.onlab.onos.net.NetTestTools; |
20 | import org.onlab.onos.net.Path; | 20 | import org.onlab.onos.net.Path; |
21 | -import org.onlab.onos.net.resource.LinkResourceRequest; | ||
22 | 21 | ||
23 | import static org.junit.Assert.assertEquals; | 22 | import static org.junit.Assert.assertEquals; |
24 | 23 | ||
... | @@ -40,11 +39,11 @@ public class PathIntentTest extends ConnectivityIntentTest { | ... | @@ -40,11 +39,11 @@ public class PathIntentTest extends ConnectivityIntentTest { |
40 | 39 | ||
41 | @Override | 40 | @Override |
42 | protected PathIntent createOne() { | 41 | protected PathIntent createOne() { |
43 | - return new PathIntent(APPID, MATCH, NOP, PATH1, new LinkResourceRequest[0]); | 42 | + return new PathIntent(APPID, MATCH, NOP, PATH1); |
44 | } | 43 | } |
45 | 44 | ||
46 | @Override | 45 | @Override |
47 | protected PathIntent createAnother() { | 46 | protected PathIntent createAnother() { |
48 | - return new PathIntent(APPID, MATCH, NOP, PATH2, new LinkResourceRequest[0]); | 47 | + return new PathIntent(APPID, MATCH, NOP, PATH2); |
49 | } | 48 | } |
50 | } | 49 | } | ... | ... |
1 | +/* | ||
2 | + * Copyright 2014 Open Networking Laboratory | ||
3 | + * | ||
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
5 | + * you may not use this file except in compliance with the License. | ||
6 | + * You may obtain a copy of the License at | ||
7 | + * | ||
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
9 | + * | ||
10 | + * Unless required by applicable law or agreed to in writing, software | ||
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
13 | + * See the License for the specific language governing permissions and | ||
14 | + * limitations under the License. | ||
15 | + */ | ||
16 | +package org.onlab.onos.net.intent.impl; | ||
17 | + | ||
18 | +import org.apache.felix.scr.annotations.Component; | ||
19 | +import org.apache.felix.scr.annotations.Reference; | ||
20 | +import org.apache.felix.scr.annotations.ReferenceCardinality; | ||
21 | +import org.onlab.onos.net.ElementId; | ||
22 | +import org.onlab.onos.net.Path; | ||
23 | +import org.onlab.onos.net.intent.ConnectivityIntent; | ||
24 | +import org.onlab.onos.net.intent.Constraint; | ||
25 | +import org.onlab.onos.net.intent.IntentCompiler; | ||
26 | +import org.onlab.onos.net.intent.IntentExtensionService; | ||
27 | +import org.onlab.onos.net.provider.ProviderId; | ||
28 | +import org.onlab.onos.net.resource.LinkResourceService; | ||
29 | +import org.onlab.onos.net.topology.LinkWeight; | ||
30 | +import org.onlab.onos.net.topology.PathService; | ||
31 | +import org.onlab.onos.net.topology.TopologyEdge; | ||
32 | + | ||
33 | +import java.util.Iterator; | ||
34 | +import java.util.List; | ||
35 | +import java.util.Set; | ||
36 | + | ||
37 | +/** | ||
38 | + * Base class for compilers of various | ||
39 | + * {@link org.onlab.onos.net.intent.ConnectivityIntent connectivity intents}. | ||
40 | + */ | ||
41 | +@Component(immediate = true) | ||
42 | +public abstract class ConnectivityIntentCompiler<T extends ConnectivityIntent> | ||
43 | + implements IntentCompiler<T> { | ||
44 | + | ||
45 | + private static final ProviderId PID = new ProviderId("core", "org.onlab.onos.core", true); | ||
46 | + | ||
47 | + @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | ||
48 | + protected IntentExtensionService intentManager; | ||
49 | + | ||
50 | + @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | ||
51 | + protected PathService pathService; | ||
52 | + | ||
53 | + @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | ||
54 | + protected LinkResourceService resourceService; | ||
55 | + | ||
56 | + /** | ||
57 | + * Returns an edge-weight capable of evaluating links on the basis of the | ||
58 | + * specified constraints. | ||
59 | + * | ||
60 | + * @param constraints path constraints | ||
61 | + * @return edge-weight function | ||
62 | + */ | ||
63 | + protected LinkWeight weight(List<Constraint> constraints) { | ||
64 | + return new ConstraintBasedLinkWeight(constraints); | ||
65 | + } | ||
66 | + | ||
67 | + /** | ||
68 | + * Validates the specified path against the given constraints. | ||
69 | + * | ||
70 | + * @param path path to be checked | ||
71 | + * @return true if the path passes all constraints | ||
72 | + */ | ||
73 | + protected boolean checkPath(Path path, List<Constraint> constraints) { | ||
74 | + for (Constraint constraint : constraints) { | ||
75 | + if (!constraint.validate(path, resourceService)) { | ||
76 | + return false; | ||
77 | + } | ||
78 | + } | ||
79 | + return true; | ||
80 | + } | ||
81 | + | ||
82 | + /** | ||
83 | + * Computes a path between two ConnectPoints. | ||
84 | + * | ||
85 | + * @param one start of the path | ||
86 | + * @param two end of the path | ||
87 | + * @return Path between the two | ||
88 | + * @throws PathNotFoundException if a path cannot be found | ||
89 | + */ | ||
90 | + protected Path getPath(ConnectivityIntent intent, | ||
91 | + ElementId one, ElementId two) { | ||
92 | + Set<Path> paths = pathService.getPaths(one, two, weight(intent.constraints())); | ||
93 | + if (paths.isEmpty()) { | ||
94 | + throw new PathNotFoundException("No packet path from " + one + " to " + two); | ||
95 | + } | ||
96 | + // TODO: let's be more intelligent about this eventually | ||
97 | + return paths.iterator().next(); | ||
98 | + } | ||
99 | + | ||
100 | + /** | ||
101 | + * Edge-weight capable of evaluating link cost using a set of constraints. | ||
102 | + */ | ||
103 | + protected class ConstraintBasedLinkWeight implements LinkWeight { | ||
104 | + | ||
105 | + private final List<Constraint> constraints; | ||
106 | + | ||
107 | + /** | ||
108 | + * Creates a new edge-weight function capable of evaluating links | ||
109 | + * on the basis of the specified constraints. | ||
110 | + * | ||
111 | + * @param constraints path constraints | ||
112 | + */ | ||
113 | + ConstraintBasedLinkWeight(List<Constraint> constraints) { | ||
114 | + this.constraints = constraints; | ||
115 | + } | ||
116 | + | ||
117 | + @Override | ||
118 | + public double weight(TopologyEdge edge) { | ||
119 | + if (constraints == null) { | ||
120 | + return 1.0; | ||
121 | + } | ||
122 | + | ||
123 | + // iterate over all constraints in order and return the weight of | ||
124 | + // the first one with fast fail over the first failure | ||
125 | + Iterator<Constraint> it = constraints.iterator(); | ||
126 | + double cost = it.next().cost(edge.link(), resourceService); | ||
127 | + while (it.hasNext() && cost > 0) { | ||
128 | + if (it.next().cost(edge.link(), resourceService) < 0) { | ||
129 | + return -1; | ||
130 | + } | ||
131 | + } | ||
132 | + return cost; | ||
133 | + } | ||
134 | + } | ||
135 | + | ||
136 | +} |
... | @@ -15,30 +15,21 @@ | ... | @@ -15,30 +15,21 @@ |
15 | */ | 15 | */ |
16 | package org.onlab.onos.net.intent.impl; | 16 | package org.onlab.onos.net.intent.impl; |
17 | 17 | ||
18 | -import java.util.Arrays; | ||
19 | -import java.util.List; | ||
20 | -import java.util.Set; | ||
21 | - | ||
22 | import org.apache.felix.scr.annotations.Activate; | 18 | import org.apache.felix.scr.annotations.Activate; |
23 | import org.apache.felix.scr.annotations.Component; | 19 | import org.apache.felix.scr.annotations.Component; |
24 | import org.apache.felix.scr.annotations.Deactivate; | 20 | import org.apache.felix.scr.annotations.Deactivate; |
25 | import org.apache.felix.scr.annotations.Reference; | 21 | import org.apache.felix.scr.annotations.Reference; |
26 | import org.apache.felix.scr.annotations.ReferenceCardinality; | 22 | import org.apache.felix.scr.annotations.ReferenceCardinality; |
27 | import org.onlab.onos.net.Host; | 23 | import org.onlab.onos.net.Host; |
28 | -import org.onlab.onos.net.HostId; | ||
29 | -import org.onlab.onos.net.Link; | ||
30 | import org.onlab.onos.net.Path; | 24 | import org.onlab.onos.net.Path; |
31 | import org.onlab.onos.net.flow.TrafficSelector; | 25 | import org.onlab.onos.net.flow.TrafficSelector; |
32 | import org.onlab.onos.net.host.HostService; | 26 | import org.onlab.onos.net.host.HostService; |
33 | import org.onlab.onos.net.intent.HostToHostIntent; | 27 | import org.onlab.onos.net.intent.HostToHostIntent; |
34 | import org.onlab.onos.net.intent.Intent; | 28 | import org.onlab.onos.net.intent.Intent; |
35 | -import org.onlab.onos.net.intent.IntentCompiler; | ||
36 | -import org.onlab.onos.net.intent.IntentExtensionService; | ||
37 | import org.onlab.onos.net.intent.PathIntent; | 29 | import org.onlab.onos.net.intent.PathIntent; |
38 | -import org.onlab.onos.net.topology.LinkWeight; | 30 | + |
39 | -import org.onlab.onos.net.resource.LinkResourceRequest; | 31 | +import java.util.Arrays; |
40 | -import org.onlab.onos.net.topology.PathService; | 32 | +import java.util.List; |
41 | -import org.onlab.onos.net.topology.TopologyEdge; | ||
42 | 33 | ||
43 | import static org.onlab.onos.net.flow.DefaultTrafficSelector.builder; | 34 | import static org.onlab.onos.net.flow.DefaultTrafficSelector.builder; |
44 | 35 | ||
... | @@ -47,13 +38,7 @@ import static org.onlab.onos.net.flow.DefaultTrafficSelector.builder; | ... | @@ -47,13 +38,7 @@ import static org.onlab.onos.net.flow.DefaultTrafficSelector.builder; |
47 | */ | 38 | */ |
48 | @Component(immediate = true) | 39 | @Component(immediate = true) |
49 | public class HostToHostIntentCompiler | 40 | public class HostToHostIntentCompiler |
50 | - implements IntentCompiler<HostToHostIntent> { | 41 | + extends ConnectivityIntentCompiler<HostToHostIntent> { |
51 | - | ||
52 | - @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | ||
53 | - protected IntentExtensionService intentManager; | ||
54 | - | ||
55 | - @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | ||
56 | - protected PathService pathService; | ||
57 | 42 | ||
58 | @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | 43 | @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) |
59 | protected HostService hostService; | 44 | protected HostService hostService; |
... | @@ -70,8 +55,8 @@ public class HostToHostIntentCompiler | ... | @@ -70,8 +55,8 @@ public class HostToHostIntentCompiler |
70 | 55 | ||
71 | @Override | 56 | @Override |
72 | public List<Intent> compile(HostToHostIntent intent) { | 57 | public List<Intent> compile(HostToHostIntent intent) { |
73 | - Path pathOne = getPath(intent.one(), intent.two()); | 58 | + Path pathOne = getPath(intent, intent.one(), intent.two()); |
74 | - Path pathTwo = getPath(intent.two(), intent.one()); | 59 | + Path pathTwo = getPath(intent, intent.two(), intent.one()); |
75 | 60 | ||
76 | Host one = hostService.getHost(intent.one()); | 61 | Host one = hostService.getHost(intent.one()); |
77 | Host two = hostService.getHost(intent.two()); | 62 | Host two = hostService.getHost(intent.two()); |
... | @@ -85,22 +70,7 @@ public class HostToHostIntentCompiler | ... | @@ -85,22 +70,7 @@ public class HostToHostIntentCompiler |
85 | HostToHostIntent intent) { | 70 | HostToHostIntent intent) { |
86 | TrafficSelector selector = builder(intent.selector()) | 71 | TrafficSelector selector = builder(intent.selector()) |
87 | .matchEthSrc(src.mac()).matchEthDst(dst.mac()).build(); | 72 | .matchEthSrc(src.mac()).matchEthDst(dst.mac()).build(); |
88 | - return new PathIntent(intent.appId(), selector, intent.treatment(), | 73 | + return new PathIntent(intent.appId(), selector, intent.treatment(), path); |
89 | - path, new LinkResourceRequest[0]); | ||
90 | } | 74 | } |
91 | 75 | ||
92 | - private Path getPath(HostId one, HostId two) { | ||
93 | - Set<Path> paths = pathService.getPaths(one, two, new LinkWeight() { | ||
94 | - @Override | ||
95 | - public double weight(TopologyEdge edge) { | ||
96 | - return edge.link().type() == Link.Type.OPTICAL ? -1 : +1; | ||
97 | - } | ||
98 | - }); | ||
99 | - | ||
100 | - if (paths.isEmpty()) { | ||
101 | - throw new PathNotFoundException("No path from host " + one + " to " + two); | ||
102 | - } | ||
103 | - // TODO: let's be more intelligent about this eventually | ||
104 | - return paths.iterator().next(); | ||
105 | - } | ||
106 | } | 76 | } | ... | ... |
... | @@ -35,10 +35,13 @@ import org.onlab.onos.net.flow.FlowRuleBatchEntry.FlowRuleOperation; | ... | @@ -35,10 +35,13 @@ import org.onlab.onos.net.flow.FlowRuleBatchEntry.FlowRuleOperation; |
35 | import org.onlab.onos.net.flow.FlowRuleBatchOperation; | 35 | import org.onlab.onos.net.flow.FlowRuleBatchOperation; |
36 | import org.onlab.onos.net.flow.TrafficSelector; | 36 | import org.onlab.onos.net.flow.TrafficSelector; |
37 | import org.onlab.onos.net.flow.TrafficTreatment; | 37 | import org.onlab.onos.net.flow.TrafficTreatment; |
38 | +import org.onlab.onos.net.intent.Constraint; | ||
38 | import org.onlab.onos.net.intent.IntentExtensionService; | 39 | import org.onlab.onos.net.intent.IntentExtensionService; |
39 | import org.onlab.onos.net.intent.IntentInstaller; | 40 | import org.onlab.onos.net.intent.IntentInstaller; |
40 | import org.onlab.onos.net.intent.PathIntent; | 41 | import org.onlab.onos.net.intent.PathIntent; |
42 | +import org.onlab.onos.net.resource.DefaultLinkResourceRequest; | ||
41 | import org.onlab.onos.net.resource.LinkResourceAllocations; | 43 | import org.onlab.onos.net.resource.LinkResourceAllocations; |
44 | +import org.onlab.onos.net.resource.LinkResourceRequest; | ||
42 | import org.onlab.onos.net.resource.LinkResourceService; | 45 | import org.onlab.onos.net.resource.LinkResourceService; |
43 | import org.slf4j.Logger; | 46 | import org.slf4j.Logger; |
44 | 47 | ||
... | @@ -79,13 +82,7 @@ public class PathIntentInstaller implements IntentInstaller<PathIntent> { | ... | @@ -79,13 +82,7 @@ public class PathIntentInstaller implements IntentInstaller<PathIntent> { |
79 | 82 | ||
80 | @Override | 83 | @Override |
81 | public List<FlowRuleBatchOperation> install(PathIntent intent) { | 84 | public List<FlowRuleBatchOperation> install(PathIntent intent) { |
82 | - if (intent.resourceRequests().length > 0) { | 85 | + LinkResourceAllocations allocations = allocateResources(intent); |
83 | - LinkResourceAllocations allocations = allocateBandwidth(intent); | ||
84 | - if (allocations == null) { | ||
85 | - log.debug("Insufficient bandwidth available to install path intent {}", intent); | ||
86 | - return null; | ||
87 | - } | ||
88 | - } | ||
89 | 86 | ||
90 | TrafficSelector.Builder builder = | 87 | TrafficSelector.Builder builder = |
91 | DefaultTrafficSelector.builder(intent.selector()); | 88 | DefaultTrafficSelector.builder(intent.selector()); |
... | @@ -110,6 +107,10 @@ public class PathIntentInstaller implements IntentInstaller<PathIntent> { | ... | @@ -110,6 +107,10 @@ public class PathIntentInstaller implements IntentInstaller<PathIntent> { |
110 | 107 | ||
111 | @Override | 108 | @Override |
112 | public List<FlowRuleBatchOperation> uninstall(PathIntent intent) { | 109 | public List<FlowRuleBatchOperation> uninstall(PathIntent intent) { |
110 | + LinkResourceAllocations allocatedResources = resourceService.getAllocations(intent.id()); | ||
111 | + if (allocatedResources != null) { | ||
112 | + resourceService.releaseResources(allocatedResources); | ||
113 | + } | ||
113 | TrafficSelector.Builder builder = | 114 | TrafficSelector.Builder builder = |
114 | DefaultTrafficSelector.builder(intent.selector()); | 115 | DefaultTrafficSelector.builder(intent.selector()); |
115 | Iterator<Link> links = intent.path().links().iterator(); | 116 | Iterator<Link> links = intent.path().links().iterator(); |
... | @@ -130,8 +131,23 @@ public class PathIntentInstaller implements IntentInstaller<PathIntent> { | ... | @@ -130,8 +131,23 @@ public class PathIntentInstaller implements IntentInstaller<PathIntent> { |
130 | return Lists.newArrayList(new FlowRuleBatchOperation(rules)); | 131 | return Lists.newArrayList(new FlowRuleBatchOperation(rules)); |
131 | } | 132 | } |
132 | 133 | ||
133 | - private LinkResourceAllocations allocateBandwidth(PathIntent intent) { | 134 | + /** |
134 | - return resourceService.requestResources(intent.resourceRequests()[0]); | 135 | + * Allocate resources required for an intent. |
136 | + * | ||
137 | + * @param intent intent to allocate resource for | ||
138 | + * @return allocated resources if any are required, null otherwise | ||
139 | + */ | ||
140 | + private LinkResourceAllocations allocateResources(PathIntent intent) { | ||
141 | + if (intent.constraints() == null) { | ||
142 | + return null; | ||
143 | + } | ||
144 | + LinkResourceRequest.Builder builder = | ||
145 | + DefaultLinkResourceRequest.builder(intent.id(), intent.path().links()); | ||
146 | + for (Constraint constraint : intent.constraints()) { | ||
147 | + builder.addConstraint(constraint); | ||
148 | + } | ||
149 | + LinkResourceRequest request = builder.build(); | ||
150 | + return request.resources().isEmpty() ? null : resourceService.requestResources(request); | ||
135 | } | 151 | } |
136 | 152 | ||
137 | // TODO refactor below this line... ---------------------------- | 153 | // TODO refactor below this line... ---------------------------- | ... | ... |
... | @@ -15,31 +15,20 @@ | ... | @@ -15,31 +15,20 @@ |
15 | */ | 15 | */ |
16 | package org.onlab.onos.net.intent.impl; | 16 | package org.onlab.onos.net.intent.impl; |
17 | 17 | ||
18 | -import java.util.ArrayList; | ||
19 | -import java.util.List; | ||
20 | -import java.util.Set; | ||
21 | - | ||
22 | import org.apache.felix.scr.annotations.Activate; | 18 | import org.apache.felix.scr.annotations.Activate; |
23 | import org.apache.felix.scr.annotations.Component; | 19 | import org.apache.felix.scr.annotations.Component; |
24 | import org.apache.felix.scr.annotations.Deactivate; | 20 | import org.apache.felix.scr.annotations.Deactivate; |
25 | -import org.apache.felix.scr.annotations.Reference; | ||
26 | -import org.apache.felix.scr.annotations.ReferenceCardinality; | ||
27 | -import org.onlab.onos.net.ConnectPoint; | ||
28 | import org.onlab.onos.net.DefaultEdgeLink; | 21 | import org.onlab.onos.net.DefaultEdgeLink; |
29 | import org.onlab.onos.net.DefaultPath; | 22 | import org.onlab.onos.net.DefaultPath; |
30 | import org.onlab.onos.net.Link; | 23 | import org.onlab.onos.net.Link; |
31 | import org.onlab.onos.net.Path; | 24 | import org.onlab.onos.net.Path; |
32 | import org.onlab.onos.net.intent.Intent; | 25 | import org.onlab.onos.net.intent.Intent; |
33 | -import org.onlab.onos.net.intent.IntentCompiler; | ||
34 | -import org.onlab.onos.net.intent.IntentExtensionService; | ||
35 | import org.onlab.onos.net.intent.PathIntent; | 26 | import org.onlab.onos.net.intent.PathIntent; |
36 | import org.onlab.onos.net.intent.PointToPointIntent; | 27 | import org.onlab.onos.net.intent.PointToPointIntent; |
37 | import org.onlab.onos.net.provider.ProviderId; | 28 | import org.onlab.onos.net.provider.ProviderId; |
38 | -import org.onlab.onos.net.resource.LinkResourceRequest; | 29 | + |
39 | -import org.onlab.onos.net.topology.LinkWeight; | 30 | +import java.util.ArrayList; |
40 | -import org.onlab.onos.net.topology.Topology; | 31 | +import java.util.List; |
41 | -import org.onlab.onos.net.topology.TopologyEdge; | ||
42 | -import org.onlab.onos.net.topology.TopologyService; | ||
43 | 32 | ||
44 | import static java.util.Arrays.asList; | 33 | import static java.util.Arrays.asList; |
45 | 34 | ||
... | @@ -48,14 +37,11 @@ import static java.util.Arrays.asList; | ... | @@ -48,14 +37,11 @@ import static java.util.Arrays.asList; |
48 | */ | 37 | */ |
49 | @Component(immediate = true) | 38 | @Component(immediate = true) |
50 | public class PointToPointIntentCompiler | 39 | public class PointToPointIntentCompiler |
51 | - implements IntentCompiler<PointToPointIntent> { | 40 | + extends ConnectivityIntentCompiler<PointToPointIntent> { |
52 | 41 | ||
53 | - private static final ProviderId PID = new ProviderId("core", "org.onlab.onos.core", true); | 42 | + // TODO: use off-the-shell core provider ID |
54 | - @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | 43 | + private static final ProviderId PID = |
55 | - protected IntentExtensionService intentManager; | 44 | + new ProviderId("core", "org.onlab.onos.core", true); |
56 | - | ||
57 | - @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | ||
58 | - protected TopologyService topologyService; | ||
59 | 45 | ||
60 | @Activate | 46 | @Activate |
61 | public void activate() { | 47 | public void activate() { |
... | @@ -69,14 +55,15 @@ public class PointToPointIntentCompiler | ... | @@ -69,14 +55,15 @@ public class PointToPointIntentCompiler |
69 | 55 | ||
70 | @Override | 56 | @Override |
71 | public List<Intent> compile(PointToPointIntent intent) { | 57 | public List<Intent> compile(PointToPointIntent intent) { |
72 | - Path path = getPath(intent.ingressPoint(), intent.egressPoint()); | 58 | + Path path = getPath(intent, intent.ingressPoint().deviceId(), |
59 | + intent.egressPoint().deviceId()); | ||
73 | 60 | ||
74 | List<Link> links = new ArrayList<>(); | 61 | List<Link> links = new ArrayList<>(); |
75 | links.add(DefaultEdgeLink.createEdgeLink(intent.ingressPoint(), true)); | 62 | links.add(DefaultEdgeLink.createEdgeLink(intent.ingressPoint(), true)); |
76 | links.addAll(path.links()); | 63 | links.addAll(path.links()); |
77 | links.add(DefaultEdgeLink.createEdgeLink(intent.egressPoint(), false)); | 64 | links.add(DefaultEdgeLink.createEdgeLink(intent.egressPoint(), false)); |
78 | 65 | ||
79 | - return asList(createPathIntent(new DefaultPath(PID, links, path.cost() + 2, | 66 | + return asList(createPathIntent(new DefaultPath(PID, links, path.cost(), |
80 | path.annotations()), intent)); | 67 | path.annotations()), intent)); |
81 | } | 68 | } |
82 | 69 | ||
... | @@ -90,34 +77,7 @@ public class PointToPointIntentCompiler | ... | @@ -90,34 +77,7 @@ public class PointToPointIntentCompiler |
90 | private Intent createPathIntent(Path path, | 77 | private Intent createPathIntent(Path path, |
91 | PointToPointIntent intent) { | 78 | PointToPointIntent intent) { |
92 | return new PathIntent(intent.appId(), | 79 | return new PathIntent(intent.appId(), |
93 | - intent.selector(), intent.treatment(), path, | 80 | + intent.selector(), intent.treatment(), path); |
94 | - new LinkResourceRequest[0]); | ||
95 | - } | ||
96 | - | ||
97 | - /** | ||
98 | - * Computes a path between two ConnectPoints. | ||
99 | - * | ||
100 | - * @param one start of the path | ||
101 | - * @param two end of the path | ||
102 | - * @return Path between the two | ||
103 | - * @throws PathNotFoundException if a path cannot be found | ||
104 | - */ | ||
105 | - private Path getPath(ConnectPoint one, ConnectPoint two) { | ||
106 | - Topology topology = topologyService.currentTopology(); | ||
107 | - LinkWeight weight = new LinkWeight() { | ||
108 | - @Override | ||
109 | - public double weight(TopologyEdge edge) { | ||
110 | - return edge.link().type() == Link.Type.OPTICAL ? -1 : +1; | ||
111 | - } | ||
112 | - }; | ||
113 | - | ||
114 | - Set<Path> paths = topologyService.getPaths(topology, one.deviceId(), | ||
115 | - two.deviceId(), weight); | ||
116 | - if (paths.isEmpty()) { | ||
117 | - throw new PathNotFoundException("No packet path from " + one + " to " + two); | ||
118 | } | 81 | } |
119 | 82 | ||
120 | - // TODO: let's be more intelligent about this eventually | ||
121 | - return paths.iterator().next(); | ||
122 | - } | ||
123 | } | 83 | } | ... | ... |
1 | -package org.onlab.onos.net.intent.impl; | ||
2 | - | ||
3 | -import java.util.ArrayList; | ||
4 | -import java.util.Arrays; | ||
5 | -import java.util.List; | ||
6 | -import java.util.Set; | ||
7 | - | ||
8 | -import org.apache.felix.scr.annotations.Activate; | ||
9 | -import org.apache.felix.scr.annotations.Component; | ||
10 | -import org.apache.felix.scr.annotations.Deactivate; | ||
11 | -import org.apache.felix.scr.annotations.Reference; | ||
12 | -import org.apache.felix.scr.annotations.ReferenceCardinality; | ||
13 | -import org.onlab.onos.net.ConnectPoint; | ||
14 | -import org.onlab.onos.net.DefaultEdgeLink; | ||
15 | -import org.onlab.onos.net.DefaultPath; | ||
16 | -import org.onlab.onos.net.Link; | ||
17 | -import org.onlab.onos.net.Path; | ||
18 | -import org.onlab.onos.net.intent.Intent; | ||
19 | -import org.onlab.onos.net.intent.IntentCompiler; | ||
20 | -import org.onlab.onos.net.intent.IntentExtensionService; | ||
21 | -import org.onlab.onos.net.intent.PathIntent; | ||
22 | -import org.onlab.onos.net.intent.PointToPointIntent; | ||
23 | -import org.onlab.onos.net.intent.PointToPointIntentWithBandwidthConstraint; | ||
24 | -import org.onlab.onos.net.provider.ProviderId; | ||
25 | -import org.onlab.onos.net.resource.BandwidthResourceRequest; | ||
26 | -import org.onlab.onos.net.resource.DefaultLinkResourceRequest; | ||
27 | -import org.onlab.onos.net.resource.LinkResourceRequest; | ||
28 | -import org.onlab.onos.net.resource.LinkResourceService; | ||
29 | -import org.onlab.onos.net.resource.ResourceRequest; | ||
30 | -import org.onlab.onos.net.resource.ResourceType; | ||
31 | -import org.onlab.onos.net.topology.LinkWeight; | ||
32 | -import org.onlab.onos.net.topology.Topology; | ||
33 | -import org.onlab.onos.net.topology.TopologyEdge; | ||
34 | -import org.onlab.onos.net.topology.TopologyService; | ||
35 | - | ||
36 | -/** | ||
37 | - * A intent compiler for {@link org.onlab.onos.net.intent.HostToHostIntent}. | ||
38 | - */ | ||
39 | -@Component(immediate = true) | ||
40 | -public class PointToPointIntentWithBandwidthConstraintCompiler | ||
41 | - implements IntentCompiler<PointToPointIntentWithBandwidthConstraint> { | ||
42 | - | ||
43 | - private static final ProviderId PID = new ProviderId("core", "org.onlab.onos.core", true); | ||
44 | - @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | ||
45 | - protected IntentExtensionService intentManager; | ||
46 | - | ||
47 | - @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | ||
48 | - protected TopologyService topologyService; | ||
49 | - | ||
50 | - @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | ||
51 | - protected LinkResourceService resourceService; | ||
52 | - | ||
53 | - @Activate | ||
54 | - public void activate() { | ||
55 | - intentManager.registerCompiler(PointToPointIntentWithBandwidthConstraint.class, this); | ||
56 | - } | ||
57 | - | ||
58 | - @Deactivate | ||
59 | - public void deactivate() { | ||
60 | - intentManager.unregisterCompiler(PointToPointIntent.class); | ||
61 | - } | ||
62 | - | ||
63 | - @Override | ||
64 | - public List<Intent> compile(PointToPointIntentWithBandwidthConstraint intent) { | ||
65 | - Path path = getPath(intent.ingressPoint(), intent.egressPoint(), intent.bandwidthRequest()); | ||
66 | - | ||
67 | - List<Link> links = new ArrayList<>(); | ||
68 | - links.add(DefaultEdgeLink.createEdgeLink(intent.ingressPoint(), true)); | ||
69 | - links.addAll(path.links()); | ||
70 | - links.add(DefaultEdgeLink.createEdgeLink(intent.egressPoint(), false)); | ||
71 | - | ||
72 | - return Arrays.asList(createPathIntent(new DefaultPath(PID, links, path.cost() + 2, | ||
73 | - path.annotations()), | ||
74 | - intent)); | ||
75 | - } | ||
76 | - | ||
77 | - /** | ||
78 | - * Creates a path intent from the specified path and original | ||
79 | - * connectivity intent. | ||
80 | - * | ||
81 | - * @param path path to create an intent for | ||
82 | - * @param intent original intent | ||
83 | - */ | ||
84 | - private Intent createPathIntent(Path path, | ||
85 | - PointToPointIntentWithBandwidthConstraint intent) { | ||
86 | - LinkResourceRequest.Builder request = DefaultLinkResourceRequest.builder(intent.id(), | ||
87 | - path.links()) | ||
88 | - // TODO - this seems awkward, maybe allow directly attaching a BandwidthRequest | ||
89 | - .addBandwidthRequest(intent.bandwidthRequest().bandwidth().toDouble()); | ||
90 | - LinkResourceRequest bandwidthRequest = request.build(); | ||
91 | - LinkResourceRequest[] bandwidthRequests = {bandwidthRequest}; | ||
92 | - return new PathIntent(intent.appId(), | ||
93 | - intent.selector(), intent.treatment(), path, | ||
94 | - bandwidthRequests); | ||
95 | - } | ||
96 | - | ||
97 | - /** | ||
98 | - * Computes a path between two ConnectPoints. | ||
99 | - * | ||
100 | - * @param one start of the path | ||
101 | - * @param two end of the path | ||
102 | - * @return Path between the two | ||
103 | - * @throws org.onlab.onos.net.intent.impl.PathNotFoundException if a path cannot be found | ||
104 | - */ | ||
105 | - private Path getPath(ConnectPoint one, ConnectPoint two, final BandwidthResourceRequest bandwidthRequest) { | ||
106 | - Topology topology = topologyService.currentTopology(); | ||
107 | - LinkWeight weight = new LinkWeight() { | ||
108 | - @Override | ||
109 | - public double weight(TopologyEdge edge) { | ||
110 | - if (bandwidthRequest != null) { | ||
111 | - double allocatedBandwidth = 0.0; | ||
112 | - Iterable<ResourceRequest> availableResources = resourceService.getAvailableResources(edge.link()); | ||
113 | - for (ResourceRequest availableResource : availableResources) { | ||
114 | - if (availableResource.type() == ResourceType.BANDWIDTH) { | ||
115 | - BandwidthResourceRequest bandwidthRequest = (BandwidthResourceRequest) availableResource; | ||
116 | - allocatedBandwidth += bandwidthRequest.bandwidth().toDouble(); | ||
117 | - } | ||
118 | - } | ||
119 | - | ||
120 | - // TODO this needs to be discovered from switch/ports somehow | ||
121 | - double maxBandwidth = 1000; | ||
122 | - | ||
123 | - double availableBandwidth = maxBandwidth - allocatedBandwidth; | ||
124 | - if (availableBandwidth >= bandwidthRequest.bandwidth().toDouble()) { | ||
125 | - return 1; | ||
126 | - } else { | ||
127 | - return -1; | ||
128 | - } | ||
129 | - } else { | ||
130 | - return 1; | ||
131 | - } | ||
132 | - } | ||
133 | - }; | ||
134 | - | ||
135 | - Set<Path> paths = topologyService.getPaths(topology, | ||
136 | - one.deviceId(), | ||
137 | - two.deviceId(), | ||
138 | - weight); | ||
139 | - | ||
140 | - if (paths.isEmpty()) { | ||
141 | - throw new PathNotFoundException("No packet path from " + one + " to " + two); | ||
142 | - } | ||
143 | - // TODO: let's be more intelligent about this eventually | ||
144 | - return paths.iterator().next(); | ||
145 | - } | ||
146 | -} |
-
Please register or login to post a comment