2 * Copyright (c) 2016 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
8 package org.opendaylight.protocol.bgp.mode.impl.base;
10 import static org.junit.Assert.assertEquals;
11 import static org.junit.Assert.assertNotEquals;
13 import java.util.Arrays;
14 import java.util.Collections;
15 import java.util.List;
16 import org.junit.Test;
17 import org.opendaylight.protocol.bgp.mode.impl.BestPathStateImpl;
18 import org.opendaylight.protocol.bgp.rib.spi.RouterId;
19 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.AsNumber;
20 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.message.rev180329.path.attributes.Attributes;
21 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.message.rev180329.path.attributes.AttributesBuilder;
22 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.message.rev180329.path.attributes.attributes.AsPathBuilder;
23 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.message.rev180329.path.attributes.attributes.LocalPrefBuilder;
24 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.message.rev180329.path.attributes.attributes.MultiExitDiscBuilder;
25 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.message.rev180329.path.attributes.attributes.OriginBuilder;
26 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.message.rev180329.path.attributes.attributes.as.path.SegmentsBuilder;
27 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.rib.rev180329.PeerId;
28 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.types.rev180329.BgpOrigin;
29 import org.opendaylight.yangtools.yang.common.Uint32;
31 public class BasePathSelectorTest {
32 private static final List<AsNumber> SEQ_SEGMENT = Arrays.asList(
33 new AsNumber(Uint32.ONE), new AsNumber(Uint32.TWO), new AsNumber(Uint32.valueOf(3)));
34 static final RouterId ROUTER_ID2 = RouterId.forPeerId(new PeerId("bgp://127.0.0.1"));
35 private static final List<AsNumber> SEQ_SEGMENT2 = Arrays.asList(
36 new AsNumber(Uint32.valueOf(20)), new AsNumber(Uint32.TWO), new AsNumber(Uint32.valueOf(3)));
37 private static final RouterId ROUTER_ID = RouterId.forAddress("127.0.0.1");
38 private static final RouterId ROUTER_ID3 = RouterId.forPeerId(new PeerId("bgp://127.0.0.2"));
39 private final BasePathSelector selector = new BasePathSelector(20L);
40 private final BestPathStateImpl state = new BestPathStateImpl(createStateFromPrefMedOriginASPath().build());
41 private final BaseBestPath originBestPath = new BaseBestPath(ROUTER_ID, this.state);
43 private static Attributes createStateFromPrefMedOrigin() {
44 AttributesBuilder dataContBuilder = new AttributesBuilder();
45 addLowerLocalRef(dataContBuilder);
46 addLowerMultiExitDisc(dataContBuilder);
47 addIgpOrigin(dataContBuilder);
48 return dataContBuilder.build();
51 protected static AttributesBuilder createStateFromPrefMedOriginASPath() {
52 AttributesBuilder dataContBuilder = new AttributesBuilder();
53 addHigherLocalRef(dataContBuilder);
54 addHigherMultiExitDisc(dataContBuilder);
55 addEgpOrigin(dataContBuilder);
56 addAsPath(dataContBuilder, SEQ_SEGMENT);
57 return dataContBuilder;
60 private static void addLowerLocalRef(final AttributesBuilder dataContBuilder) {
61 dataContBuilder.setLocalPref(new LocalPrefBuilder().setPref(Uint32.valueOf(123)).build());
64 private static void addHigherLocalRef(final AttributesBuilder dataContBuilder) {
65 dataContBuilder.setLocalPref(new LocalPrefBuilder().setPref(Uint32.valueOf(321)).build());
68 private static void addLowerMultiExitDisc(final AttributesBuilder dataContBuilder) {
69 dataContBuilder.setMultiExitDisc(new MultiExitDiscBuilder().setMed(Uint32.valueOf(1234)).build());
72 private static void addHigherMultiExitDisc(final AttributesBuilder dataContBuilder) {
73 dataContBuilder.setMultiExitDisc(new MultiExitDiscBuilder().setMed(Uint32.valueOf(4321)).build());
76 private static void addIgpOrigin(final AttributesBuilder dataContBuilder) {
77 dataContBuilder.setOrigin(new OriginBuilder().setValue(BgpOrigin.Igp).build());
80 private static void addEgpOrigin(final AttributesBuilder dataContBuilder) {
81 dataContBuilder.setOrigin(new OriginBuilder().setValue(BgpOrigin.Egp).build());
84 private static void addAsPath(final AttributesBuilder dataContBuilder, final List<AsNumber> segment) {
85 dataContBuilder.setAsPath(new AsPathBuilder().setSegments(
86 Collections.singletonList(new SegmentsBuilder().setAsSequence(segment).build())).build());
90 public void testBestPathWithHigherLocalPref() {
91 this.selector.processPath(ROUTER_ID2, createStateFromPrefMedOrigin()); // local-pref 123
92 BaseBestPath processedPath = this.selector.result();
93 assertEquals(123L, processedPath.getState().getLocalPref().longValue());
95 this.selector.processPath(ROUTER_ID2, createStateFromPrefMedOriginASPath().build()); // local-pref 321
96 processedPath = this.selector.result();
97 assertEquals(321L, processedPath.getState().getLocalPref().longValue());
99 AttributesBuilder dataContBuilder = new AttributesBuilder();
100 addLowerLocalRef(dataContBuilder); // prefer path with higher LOCAL_PREF
101 this.selector.processPath(ROUTER_ID2, dataContBuilder.build());
102 processedPath = this.selector.result();
103 assertEquals(321L, processedPath.getState().getLocalPref().longValue());
107 public void testBestPathForEquality() {
108 this.selector.processPath(ROUTER_ID2, createStateFromPrefMedOriginASPath().build());
109 final BaseBestPath processedPath = this.selector.result();
111 assertEquals(this.originBestPath.getPeerId(), processedPath.getPeerId());
112 assertEquals(this.originBestPath.getState().getLocalPref(), processedPath.getState().getLocalPref());
113 assertEquals(this.originBestPath.getState().getMultiExitDisc(), processedPath.getState().getMultiExitDisc());
114 assertEquals(this.originBestPath.getState().getOrigin(), processedPath.getState().getOrigin());
115 assertEquals(this.originBestPath.getState().getPeerAs(), processedPath.getState().getPeerAs());
116 assertEquals(this.originBestPath.getState().getAsPathLength(), processedPath.getState().getAsPathLength());
120 public void testBestPathSelectionOptions() {
121 AttributesBuilder dataContBuilder = createStateFromPrefMedOriginASPath();
122 this.selector.processPath(ROUTER_ID2, dataContBuilder.build());
123 BaseBestPath processedPath = this.selector.result();
124 assertEquals(1, processedPath.getState().getOrigin().getIntValue());
126 addIgpOrigin(dataContBuilder); // prefer the path with the lowest origin type
127 this.selector.processPath(ROUTER_ID2, dataContBuilder.build());
128 processedPath = this.selector.result();
129 assertEquals(0, processedPath.getState().getOrigin().getIntValue());
131 addEgpOrigin(dataContBuilder);
132 this.selector.processPath(ROUTER_ID2, dataContBuilder.build());
133 processedPath = this.selector.result();
134 assertEquals(0, processedPath.getState().getOrigin().getIntValue());
136 // prefer the path with the lowest multi-exit discriminator (MED)
137 assertEquals(4321L, processedPath.getState().getMultiExitDisc());
138 addIgpOrigin(dataContBuilder);
139 addLowerMultiExitDisc(dataContBuilder);
140 this.selector.processPath(ROUTER_ID2, dataContBuilder.build());
141 processedPath = this.selector.result();
142 assertEquals(1234L, processedPath.getState().getMultiExitDisc());
144 addHigherMultiExitDisc(dataContBuilder);
145 this.selector.processPath(ROUTER_ID2, dataContBuilder.build());
146 processedPath = this.selector.result();
147 assertEquals(1234L, processedPath.getState().getMultiExitDisc());
149 addLowerMultiExitDisc(dataContBuilder);
150 addAsPath(dataContBuilder, SEQ_SEGMENT2);
151 assertEquals(1L, processedPath.getState().getPeerAs());
152 assertEquals(3, processedPath.getState().getAsPathLength());
153 this.selector.processPath(ROUTER_ID2, dataContBuilder.build());
154 processedPath = this.selector.result();
155 assertEquals(1L, processedPath.getState().getPeerAs());
156 assertEquals(3, processedPath.getState().getAsPathLength());
160 public void testBestPathForNonEquality() {
161 this.selector.processPath(ROUTER_ID3, createStateFromPrefMedOrigin());
162 final BaseBestPath processedPath = this.selector.result();
164 assertNotEquals(this.originBestPath.getPeerId(), processedPath.getPeerId());
165 assertNotEquals(this.originBestPath.getState().getLocalPref(), processedPath.getState().getLocalPref());
166 assertNotEquals(this.originBestPath.getState().getMultiExitDisc(), processedPath.getState().getMultiExitDisc());
167 assertNotEquals(this.originBestPath.getState().getOrigin(), processedPath.getState().getOrigin());
168 assertNotEquals(this.originBestPath.getState().getPeerAs(), processedPath.getState().getPeerAs());
169 assertNotEquals(this.originBestPath.getState().getAsPathLength(), processedPath.getState().getAsPathLength());
173 public void testBgpOrigin() {
174 this.selector.processPath(ROUTER_ID3, new AttributesBuilder().setOrigin(new OriginBuilder()
175 .setValue(BgpOrigin.Incomplete).build()).build());
176 final BaseBestPath processedPathIncom = this.selector.result();
177 assertEquals(BgpOrigin.Incomplete, processedPathIncom.getState().getOrigin());