[ONOS-3410] Let sdn-ip support default route
Default route is an important and frequntly used feature in BGP. For example, network operators want to reduce the size of the route table. The current sdn-ip does not support this feature. So this patch is to let sdn-ip support this feature. Change-Id: Ibb5afe3711522468e4902da2e090370db71b29da
Showing
3 changed files
with
31 additions
and
16 deletions
... | @@ -89,14 +89,17 @@ public class RouteEntry { | ... | @@ -89,14 +89,17 @@ public class RouteEntry { |
89 | /** | 89 | /** |
90 | * Creates the binary string representation of an IP prefix. | 90 | * Creates the binary string representation of an IP prefix. |
91 | * The prefix can be either IPv4 or IPv6. | 91 | * The prefix can be either IPv4 or IPv6. |
92 | - * The string length is equal to the prefix length. | 92 | + * The string length is equal to the prefix length + 1. |
93 | + * | ||
94 | + * For each string, we put a extra "0" in the front. The purpose of | ||
95 | + * doing this is to store the default route inside InvertedRadixTree. | ||
93 | * | 96 | * |
94 | * @param ipPrefix the IP prefix to use | 97 | * @param ipPrefix the IP prefix to use |
95 | * @return the binary string representation | 98 | * @return the binary string representation |
96 | */ | 99 | */ |
97 | public static String createBinaryString(IpPrefix ipPrefix) { | 100 | public static String createBinaryString(IpPrefix ipPrefix) { |
98 | if (ipPrefix.prefixLength() == 0) { | 101 | if (ipPrefix.prefixLength() == 0) { |
99 | - return ""; | 102 | + return "0"; |
100 | } | 103 | } |
101 | 104 | ||
102 | byte[] octets = ipPrefix.address().toOctets(); | 105 | byte[] octets = ipPrefix.address().toOctets(); |
... | @@ -109,7 +112,8 @@ public class RouteEntry { | ... | @@ -109,7 +112,8 @@ public class RouteEntry { |
109 | boolean isSet = ((value & mask) != 0); | 112 | boolean isSet = ((value & mask) != 0); |
110 | result.append(isSet ? "1" : "0"); | 113 | result.append(isSet ? "1" : "0"); |
111 | } | 114 | } |
112 | - return result.toString(); | 115 | + |
116 | + return "0" + result.toString(); | ||
113 | } | 117 | } |
114 | 118 | ||
115 | @Override | 119 | @Override | ... | ... |
... | @@ -121,52 +121,52 @@ public class RouteEntryTest { | ... | @@ -121,52 +121,52 @@ public class RouteEntryTest { |
121 | Ip4Prefix prefix; | 121 | Ip4Prefix prefix; |
122 | 122 | ||
123 | prefix = Ip4Prefix.valueOf("0.0.0.0/0"); | 123 | prefix = Ip4Prefix.valueOf("0.0.0.0/0"); |
124 | - assertThat(RouteEntry.createBinaryString(prefix), is("")); | 124 | + assertThat(RouteEntry.createBinaryString(prefix), is("0")); |
125 | 125 | ||
126 | prefix = Ip4Prefix.valueOf("192.168.166.0/22"); | 126 | prefix = Ip4Prefix.valueOf("192.168.166.0/22"); |
127 | assertThat(RouteEntry.createBinaryString(prefix), | 127 | assertThat(RouteEntry.createBinaryString(prefix), |
128 | - is("1100000010101000101001")); | 128 | + is("0" + "1100000010101000101001")); |
129 | 129 | ||
130 | prefix = Ip4Prefix.valueOf("192.168.166.0/23"); | 130 | prefix = Ip4Prefix.valueOf("192.168.166.0/23"); |
131 | assertThat(RouteEntry.createBinaryString(prefix), | 131 | assertThat(RouteEntry.createBinaryString(prefix), |
132 | - is("11000000101010001010011")); | 132 | + is("0" + "11000000101010001010011")); |
133 | 133 | ||
134 | prefix = Ip4Prefix.valueOf("192.168.166.0/24"); | 134 | prefix = Ip4Prefix.valueOf("192.168.166.0/24"); |
135 | assertThat(RouteEntry.createBinaryString(prefix), | 135 | assertThat(RouteEntry.createBinaryString(prefix), |
136 | - is("110000001010100010100110")); | 136 | + is("0" + "110000001010100010100110")); |
137 | 137 | ||
138 | prefix = Ip4Prefix.valueOf("130.162.10.1/25"); | 138 | prefix = Ip4Prefix.valueOf("130.162.10.1/25"); |
139 | assertThat(RouteEntry.createBinaryString(prefix), | 139 | assertThat(RouteEntry.createBinaryString(prefix), |
140 | - is("1000001010100010000010100")); | 140 | + is("0" + "1000001010100010000010100")); |
141 | 141 | ||
142 | prefix = Ip4Prefix.valueOf("255.255.255.255/32"); | 142 | prefix = Ip4Prefix.valueOf("255.255.255.255/32"); |
143 | assertThat(RouteEntry.createBinaryString(prefix), | 143 | assertThat(RouteEntry.createBinaryString(prefix), |
144 | - is("11111111111111111111111111111111")); | 144 | + is("0" + "11111111111111111111111111111111")); |
145 | 145 | ||
146 | Ip6Prefix prefix6; | 146 | Ip6Prefix prefix6; |
147 | Pattern pattern; | 147 | Pattern pattern; |
148 | Matcher matcher; | 148 | Matcher matcher; |
149 | 149 | ||
150 | prefix6 = Ip6Prefix.valueOf("::/0"); | 150 | prefix6 = Ip6Prefix.valueOf("::/0"); |
151 | - assertThat(RouteEntry.createBinaryString(prefix6), is("")); | 151 | + assertThat(RouteEntry.createBinaryString(prefix6), is("0")); |
152 | 152 | ||
153 | prefix6 = Ip6Prefix.valueOf("2000::1000/112"); | 153 | prefix6 = Ip6Prefix.valueOf("2000::1000/112"); |
154 | - pattern = Pattern.compile("00100{108}"); | 154 | + pattern = Pattern.compile("0" + "00100{108}"); |
155 | matcher = pattern.matcher(RouteEntry.createBinaryString(prefix6)); | 155 | matcher = pattern.matcher(RouteEntry.createBinaryString(prefix6)); |
156 | assertTrue(matcher.matches()); | 156 | assertTrue(matcher.matches()); |
157 | 157 | ||
158 | prefix6 = Ip6Prefix.valueOf("2000::1000/116"); | 158 | prefix6 = Ip6Prefix.valueOf("2000::1000/116"); |
159 | - pattern = Pattern.compile("00100{108}0001"); | 159 | + pattern = Pattern.compile("0" + "00100{108}0001"); |
160 | matcher = pattern.matcher(RouteEntry.createBinaryString(prefix6)); | 160 | matcher = pattern.matcher(RouteEntry.createBinaryString(prefix6)); |
161 | assertTrue(matcher.matches()); | 161 | assertTrue(matcher.matches()); |
162 | 162 | ||
163 | prefix6 = Ip6Prefix.valueOf("2000::2000/116"); | 163 | prefix6 = Ip6Prefix.valueOf("2000::2000/116"); |
164 | - pattern = Pattern.compile("00100{108}0010"); | 164 | + pattern = Pattern.compile("0" + "00100{108}0010"); |
165 | matcher = pattern.matcher(RouteEntry.createBinaryString(prefix6)); | 165 | matcher = pattern.matcher(RouteEntry.createBinaryString(prefix6)); |
166 | assertTrue(matcher.matches()); | 166 | assertTrue(matcher.matches()); |
167 | 167 | ||
168 | prefix6 = Ip6Prefix.valueOf("2000::1234/128"); | 168 | prefix6 = Ip6Prefix.valueOf("2000::1234/128"); |
169 | - pattern = Pattern.compile("00100{108}0001001000110100"); | 169 | + pattern = Pattern.compile("0" + "00100{108}0001001000110100"); |
170 | matcher = pattern.matcher(RouteEntry.createBinaryString(prefix6)); | 170 | matcher = pattern.matcher(RouteEntry.createBinaryString(prefix6)); |
171 | assertTrue(matcher.matches()); | 171 | assertTrue(matcher.matches()); |
172 | } | 172 | } | ... | ... |
... | @@ -83,7 +83,8 @@ public class SdnIpFib implements FibListener { | ... | @@ -83,7 +83,8 @@ public class SdnIpFib implements FibListener { |
83 | 83 | ||
84 | 84 | ||
85 | @Override | 85 | @Override |
86 | - public void update(Collection<FibUpdate> updates, Collection<FibUpdate> withdraws) { | 86 | + public void update(Collection<FibUpdate> updates, |
87 | + Collection<FibUpdate> withdraws) { | ||
87 | int submitCount = 0, withdrawCount = 0; | 88 | int submitCount = 0, withdrawCount = 0; |
88 | // | 89 | // |
89 | // NOTE: Semantically, we MUST withdraw existing intents before | 90 | // NOTE: Semantically, we MUST withdraw existing intents before |
... | @@ -157,7 +158,8 @@ public class SdnIpFib implements FibListener { | ... | @@ -157,7 +158,8 @@ public class SdnIpFib implements FibListener { |
157 | MacAddress nextHopMacAddress) { | 158 | MacAddress nextHopMacAddress) { |
158 | 159 | ||
159 | // Find the attachment point (egress interface) of the next hop | 160 | // Find the attachment point (egress interface) of the next hop |
160 | - Interface egressInterface = interfaceService.getMatchingInterface(nextHopIpAddress); | 161 | + Interface egressInterface = |
162 | + interfaceService.getMatchingInterface(nextHopIpAddress); | ||
161 | if (egressInterface == null) { | 163 | if (egressInterface == null) { |
162 | log.warn("No outgoing interface found for {}", | 164 | log.warn("No outgoing interface found for {}", |
163 | nextHopIpAddress); | 165 | nextHopIpAddress); |
... | @@ -182,12 +184,21 @@ public class SdnIpFib implements FibListener { | ... | @@ -182,12 +184,21 @@ public class SdnIpFib implements FibListener { |
182 | TrafficSelector.Builder selector = DefaultTrafficSelector.builder(); | 184 | TrafficSelector.Builder selector = DefaultTrafficSelector.builder(); |
183 | if (prefix.isIp4()) { | 185 | if (prefix.isIp4()) { |
184 | selector.matchEthType(Ethernet.TYPE_IPV4); | 186 | selector.matchEthType(Ethernet.TYPE_IPV4); |
187 | + // if it is default route, then we do not need match destination | ||
188 | + // IP address | ||
189 | + if (prefix.prefixLength() != 0) { | ||
185 | selector.matchIPDst(prefix); | 190 | selector.matchIPDst(prefix); |
191 | + } | ||
186 | } else { | 192 | } else { |
187 | selector.matchEthType(Ethernet.TYPE_IPV6); | 193 | selector.matchEthType(Ethernet.TYPE_IPV6); |
194 | + // if it is default route, then we do not need match destination | ||
195 | + // IP address | ||
196 | + if (prefix.prefixLength() != 0) { | ||
188 | selector.matchIPv6Dst(prefix); | 197 | selector.matchIPv6Dst(prefix); |
189 | } | 198 | } |
190 | 199 | ||
200 | + } | ||
201 | + | ||
191 | // Rewrite the destination MAC address | 202 | // Rewrite the destination MAC address |
192 | TrafficTreatment.Builder treatment = DefaultTrafficTreatment.builder() | 203 | TrafficTreatment.Builder treatment = DefaultTrafficTreatment.builder() |
193 | .setEthDst(nextHopMacAddress); | 204 | .setEthDst(nextHopMacAddress); | ... | ... |
-
Please register or login to post a comment