Committed by
Gerrit Code Review
ProxyArp: Reply directly when we know an external target host
Change-Id: I38773dcdcae05506c678c2006d1f63306af6b383
Showing
2 changed files
with
35 additions
and
34 deletions
... | @@ -146,9 +146,9 @@ public class ProxyArpManager implements ProxyArpService { | ... | @@ -146,9 +146,9 @@ public class ProxyArpManager implements ProxyArpService { |
146 | 146 | ||
147 | VlanId vlan = VlanId.vlanId(eth.getVlanID()); | 147 | VlanId vlan = VlanId.vlanId(eth.getVlanID()); |
148 | 148 | ||
149 | + if (isOutsidePort(inPort)) { | ||
149 | // If the request came from outside the network, only reply if it was | 150 | // If the request came from outside the network, only reply if it was |
150 | // for one of our external addresses. | 151 | // for one of our external addresses. |
151 | - if (isOutsidePort(inPort)) { | ||
152 | Set<PortAddresses> addressSet = | 152 | Set<PortAddresses> addressSet = |
153 | hostService.getAddressBindingsForPort(inPort); | 153 | hostService.getAddressBindingsForPort(inPort); |
154 | 154 | ||
... | @@ -162,10 +162,33 @@ public class ProxyArpManager implements ProxyArpService { | ... | @@ -162,10 +162,33 @@ public class ProxyArpManager implements ProxyArpService { |
162 | } | 162 | } |
163 | } | 163 | } |
164 | return; | 164 | return; |
165 | - } else { | 165 | + } |
166 | + | ||
167 | + // See if we have the target host in the host store | ||
168 | + | ||
169 | + Set<Host> hosts = hostService.getHostsByIp(targetAddress); | ||
170 | + | ||
171 | + Host dst = null; | ||
172 | + Host src = hostService.getHost(HostId.hostId(eth.getSourceMAC(), | ||
173 | + VlanId.vlanId(eth.getVlanID()))); | ||
174 | + | ||
175 | + for (Host host : hosts) { | ||
176 | + if (host.vlan().equals(vlan)) { | ||
177 | + dst = host; | ||
178 | + break; | ||
179 | + } | ||
180 | + } | ||
181 | + | ||
182 | + if (src != null && dst != null) { | ||
183 | + // We know the target host so we can respond | ||
184 | + Ethernet arpReply = buildArpReply(targetAddress, dst.mac(), eth); | ||
185 | + sendTo(arpReply, inPort); | ||
186 | + return; | ||
187 | + } | ||
188 | + | ||
166 | // If the source address matches one of our external addresses | 189 | // If the source address matches one of our external addresses |
167 | // it could be a request from an internal host to an external | 190 | // it could be a request from an internal host to an external |
168 | - // address. Forward it over to the correct ports. | 191 | + // address. Forward it over to the correct port. |
169 | Ip4Address source = | 192 | Ip4Address source = |
170 | Ip4Address.valueOf(arp.getSenderProtocolAddress()); | 193 | Ip4Address.valueOf(arp.getSenderProtocolAddress()); |
171 | Set<PortAddresses> sourceAddresses = findPortsInSubnet(source); | 194 | Set<PortAddresses> sourceAddresses = findPortsInSubnet(source); |
... | @@ -184,39 +207,15 @@ public class ProxyArpManager implements ProxyArpService { | ... | @@ -184,39 +207,15 @@ public class ProxyArpManager implements ProxyArpService { |
184 | if (matched) { | 207 | if (matched) { |
185 | return; | 208 | return; |
186 | } | 209 | } |
187 | - } | ||
188 | - | ||
189 | - // Continue with normal proxy ARP case | ||
190 | 210 | ||
191 | - Set<Host> hosts = hostService.getHostsByIp(targetAddress); | ||
192 | - | ||
193 | - Host dst = null; | ||
194 | - Host src = hostService.getHost(HostId.hostId(eth.getSourceMAC(), | ||
195 | - VlanId.vlanId(eth.getVlanID()))); | ||
196 | - | ||
197 | - for (Host host : hosts) { | ||
198 | - if (host.vlan().equals(vlan)) { | ||
199 | - dst = host; | ||
200 | - break; | ||
201 | - } | ||
202 | - } | ||
203 | - | ||
204 | - if (src == null || dst == null) { | ||
205 | // | 211 | // |
206 | // The request couldn't be resolved. | 212 | // The request couldn't be resolved. |
207 | - // Flood the request on all ports except the incoming ports. | 213 | + // Flood the request on all ports except the incoming port. |
208 | // | 214 | // |
209 | flood(eth, inPort); | 215 | flood(eth, inPort); |
210 | return; | 216 | return; |
211 | } | 217 | } |
212 | 218 | ||
213 | - // | ||
214 | - // Reply on the port the request was received on | ||
215 | - // | ||
216 | - Ethernet arpReply = buildArpReply(targetAddress, dst.mac(), eth); | ||
217 | - sendTo(arpReply, inPort); | ||
218 | - } | ||
219 | - | ||
220 | private void replyNdp(Ethernet eth, ConnectPoint inPort) { | 219 | private void replyNdp(Ethernet eth, ConnectPoint inPort) { |
221 | 220 | ||
222 | IPv6 ipv6 = (IPv6) eth.getPayload(); | 221 | IPv6 ipv6 = (IPv6) eth.getPayload(); | ... | ... |
... | @@ -242,8 +242,8 @@ public class ProxyArpManagerTest { | ... | @@ -242,8 +242,8 @@ public class ProxyArpManagerTest { |
242 | } | 242 | } |
243 | 243 | ||
244 | /** | 244 | /** |
245 | - * Tests {@link ProxyArpManager#isKnown(Ip4Address)} in the case where the | 245 | + * Tests {@link ProxyArpManager#isKnown(org.onlab.packet.IpAddress)} in the |
246 | - * IP address is not known. | 246 | + * case where the IP address is not known. |
247 | * Verifies the method returns false. | 247 | * Verifies the method returns false. |
248 | */ | 248 | */ |
249 | @Test | 249 | @Test |
... | @@ -255,8 +255,8 @@ public class ProxyArpManagerTest { | ... | @@ -255,8 +255,8 @@ public class ProxyArpManagerTest { |
255 | } | 255 | } |
256 | 256 | ||
257 | /** | 257 | /** |
258 | - * Tests {@link ProxyArpManager#isKnown(Ip4Address)} in the case where the | 258 | + * Tests {@link ProxyArpManager#isKnown(org.onlab.packet.IpAddress)} in the |
259 | - * IP address is known. | 259 | + * case where the IP address is known. |
260 | * Verifies the method returns true. | 260 | * Verifies the method returns true. |
261 | */ | 261 | */ |
262 | @Test | 262 | @Test |
... | @@ -403,12 +403,14 @@ public class ProxyArpManagerTest { | ... | @@ -403,12 +403,14 @@ public class ProxyArpManagerTest { |
403 | 403 | ||
404 | @Test | 404 | @Test |
405 | public void testReplyToRequestFromUs() { | 405 | public void testReplyToRequestFromUs() { |
406 | - replay(hostService); // no further host service expectations | ||
407 | - | ||
408 | Ip4Address ourIp = Ip4Address.valueOf("10.0.1.1"); | 406 | Ip4Address ourIp = Ip4Address.valueOf("10.0.1.1"); |
409 | MacAddress ourMac = MacAddress.valueOf(1L); | 407 | MacAddress ourMac = MacAddress.valueOf(1L); |
410 | Ip4Address theirIp = Ip4Address.valueOf("10.0.1.100"); | 408 | Ip4Address theirIp = Ip4Address.valueOf("10.0.1.100"); |
411 | 409 | ||
410 | + expect(hostService.getHostsByIp(theirIp)).andReturn(Collections.emptySet()); | ||
411 | + expect(hostService.getHost(HostId.hostId(ourMac, VLAN1))).andReturn(null); | ||
412 | + replay(hostService); | ||
413 | + | ||
412 | // This is a request from something inside our network (like a BGP | 414 | // This is a request from something inside our network (like a BGP |
413 | // daemon) to an external host. | 415 | // daemon) to an external host. |
414 | Ethernet arpRequest = buildArp(ARP.OP_REQUEST, ourMac, null, ourIp, theirIp); | 416 | Ethernet arpRequest = buildArp(ARP.OP_REQUEST, ourMac, null, ourIp, theirIp); | ... | ... |
-
Please register or login to post a comment