[ipxe-devel] Link local routing
Brian Rak
brak at gameservers.com
Fri Oct 3 20:54:42 UTC 2014
On 10/3/2014 3:42 PM, Brian Rak wrote:
> How can I get iPXE to recognize link-local (RFC 3927) routes as
> actually being link-local. For these, it shouldn't direct the packets
> to the gateway.
>
> Is there a way I can accomplish this? If I just provide iPXE with a
> normal DHCP lease, it tries to route the link local packets to the
> gateway, which doesn't work. I can't seem to find any commands that
> would allow adding a static route, nor does iPXE accept option 121.
>
> For reference, the linux routing table entry for this looks like:
>
> Destination Gateway Genmask Flags Metric Ref Use
> Iface
> 169.254.0.0 0.0.0.0 255.255.0.0 U 1004 0 0 br0
>
> _______________________________________________
> ipxe-devel mailing list
> ipxe-devel at lists.ipxe.org
> https://lists.ipxe.org/mailman/listinfo.cgi/ipxe-devel
It seems there's more to this then just adding the route. I added this
terrible patch to start populating the route:
diff --git a/src/net/ipv4.c b/src/net/ipv4.c
index 9c5cf2e..ab89389
--- a/src/net/ipv4.c
+++ b/src/net/ipv4.c
@@ -750,6 +750,13 @@ static int ipv4_create_routes ( void ) {
/* Create a route for each configured network device */
for_each_netdev ( netdev ) {
+
+ parse_ipv4_setting( NULL, "169.254.0.0", &address,
sizeof(address) );
+
+ netmask.s_addr = htonl ( IN_CLASSB_NET );
+ struct in_addr ll = { 0 };
+ add_ipv4_miniroute( netdev, address, netmask, ll );
+
settings = netdev_settings ( netdev );
/* Get IPv4 address */
address.s_addr = 0;
Which seems to have added the route (see attachment). However, it also
makes iPXE start sending weird ARP requests:
16:18:50.968492 52:54:00:9e:be:28 > Broadcast, ethertype ARP (0x0806),
length 42: Request who-has 169.254.169.254 tell 169.254.0.0, length 28
16:18:51.341807 52:54:00:9e:be:28 > Broadcast, ethertype ARP (0x0806),
length 42: Request who-has 169.254.169.254 tell 169.254.0.0, length 28
It *should* be specifying it's address as the address it got from DHCP
(216.155.132.252 in this case).
I looked at it a bit more, and ultimately came up with this:
diff --git a/src/include/ipxe/in.h b/src/include/ipxe/in.h
index de96ca2..33f5edf
--- a/src/include/ipxe/in.h
+++ b/src/include/ipxe/in.h
@@ -26,7 +26,8 @@ FILE_LICENCE ( GPL2_OR_LATER );
#define IN_CLASSC(addr) ( ( (addr) & 0xe0000000 ) ==
0xc0000000 )
#define IN_CLASSC_NET 0xffffff00
#define IN_MULTICAST(addr) ( ( (addr) & 0xf0000000 ) == 0xe0000000 )
-
+// Link local addresses (RFC 3927) are 169.254.0.0/16
+#define IN_LINKLOCAL(addr) ( ( (addr) & 0xA9FE0000 ) == 0xA9FE0000 )
/**
* IP address structure
*/
diff --git a/src/net/ipv4.c b/src/net/ipv4.c
index 9c5cf2e..ee8770e
--- a/src/net/ipv4.c
+++ b/src/net/ipv4.c
@@ -358,6 +358,14 @@ static int ipv4_tx ( struct io_buffer *iobuf,
netdev->name, strerror ( rc ) );
return rc;
}
+ } else if ( IN_LINKLOCAL ( ntohl ( iphdr->dest.s_addr ) ) ) {
+ if ( ( rc = arp_tx ( iobuf, netdev, &ipv4_protocol, &iphdr->dest,
+ &iphdr->src, netdev->ll_addr ) ) != 0 ) {
+ DBGC ( sin_dest->sin_addr, "IPv4 could not transmit "
+ "packet via %s: %s\n",
+ netdev->name, strerror ( rc ) );
+ return rc;
+ }
} else {
if ( ( rc = arp_tx ( iobuf, netdev, &ipv4_protocol,
&next_hop,
&iphdr->src, netdev->ll_addr ) )
!= 0 ) {
Basically, if it's a link local address (defined as being in the
169.254.0.0/16 block), just try to transmit directly via the destination
address, ignoring the usual next-hop.
-------------- next part --------------
A non-text attachment was scrubbed...
Name: ipxe.png
Type: image/png
Size: 2200 bytes
Desc: not available
URL: <http://lists.ipxe.org/pipermail/ipxe-devel/attachments/20141003/1f8e2b5e/attachment.png>
More information about the ipxe-devel
mailing list