Browse Source

[netdevice] Split multicast hashing out into an mc_hash method

Multicast hashing is an ugly overlap between network and link layers.
EFI requires us to provide access to this functionality, so move it
out of ipv4.c and expose it as a method of the link layer.
tags/v0.9.6
Michael Brown 16 years ago
parent
commit
6b9cc25556
4 changed files with 57 additions and 14 deletions
  1. 16
    0
      src/drivers/net/ipoib.c
  2. 10
    0
      src/include/gpxe/netdevice.h
  3. 30
    2
      src/net/ethernet.c
  4. 1
    12
      src/net/ipv4.c

+ 16
- 0
src/drivers/net/ipoib.c View File

222
 	return buf;
222
 	return buf;
223
 }
223
 }
224
 
224
 
225
+/**
226
+ * Hash multicast address
227
+ *
228
+ * @v af		Address family
229
+ * @v net_addr		Network-layer address
230
+ * @v ll_addr		Link-layer address to fill in
231
+ * @ret rc		Return status code
232
+ */
233
+static int ipoib_mc_hash ( unsigned int af __unused,
234
+			   const void *net_addr __unused,
235
+			   void *ll_addr __unused ) {
236
+
237
+	return -ENOTSUP;
238
+}
239
+
225
 /** IPoIB protocol */
240
 /** IPoIB protocol */
226
 struct ll_protocol ipoib_protocol __ll_protocol = {
241
 struct ll_protocol ipoib_protocol __ll_protocol = {
227
 	.name		= "IPoIB",
242
 	.name		= "IPoIB",
232
 	.push		= ipoib_push,
247
 	.push		= ipoib_push,
233
 	.pull		= ipoib_pull,
248
 	.pull		= ipoib_pull,
234
 	.ntoa		= ipoib_ntoa,
249
 	.ntoa		= ipoib_ntoa,
250
+	.mc_hash	= ipoib_mc_hash,
235
 };
251
 };
236
 
252
 
237
 /****************************************************************************
253
 /****************************************************************************

+ 10
- 0
src/include/gpxe/netdevice.h View File

120
 	 * allocated.
120
 	 * allocated.
121
 	 */
121
 	 */
122
 	const char * ( * ntoa ) ( const void * ll_addr );
122
 	const char * ( * ntoa ) ( const void * ll_addr );
123
+	/**
124
+	 * Hash multicast address
125
+	 *
126
+	 * @v af	Address family
127
+	 * @v net_addr	Network-layer address
128
+	 * @v ll_addr	Link-layer address to fill in
129
+	 * @ret rc	Return status code
130
+	 */
131
+	int ( * mc_hash ) ( unsigned int af, const void *net_addr,
132
+			    void *ll_addr );
123
 	/** Link-layer protocol
133
 	/** Link-layer protocol
124
 	 *
134
 	 *
125
 	 * This is an ARPHRD_XXX constant, in network byte order.
135
 	 * This is an ARPHRD_XXX constant, in network byte order.

+ 30
- 2
src/net/ethernet.c View File

24
 #include <assert.h>
24
 #include <assert.h>
25
 #include <gpxe/if_arp.h>
25
 #include <gpxe/if_arp.h>
26
 #include <gpxe/if_ether.h>
26
 #include <gpxe/if_ether.h>
27
+#include <gpxe/in.h>
27
 #include <gpxe/netdevice.h>
28
 #include <gpxe/netdevice.h>
28
 #include <gpxe/iobuf.h>
29
 #include <gpxe/iobuf.h>
29
 #include <gpxe/ethernet.h>
30
 #include <gpxe/ethernet.h>
92
 /**
93
 /**
93
  * Transcribe Ethernet address
94
  * Transcribe Ethernet address
94
  *
95
  *
95
- * @v ll_addr	Link-layer address
96
- * @ret string	Link-layer address in human-readable format
96
+ * @v ll_addr		Link-layer address
97
+ * @ret string		Link-layer address in human-readable format
97
  */
98
  */
98
 const char * eth_ntoa ( const void *ll_addr ) {
99
 const char * eth_ntoa ( const void *ll_addr ) {
99
 	static char buf[18]; /* "00:00:00:00:00:00" */
100
 	static char buf[18]; /* "00:00:00:00:00:00" */
105
 	return buf;
106
 	return buf;
106
 }
107
 }
107
 
108
 
109
+/**
110
+ * Hash multicast address
111
+ *
112
+ * @v af		Address family
113
+ * @v net_addr		Network-layer address
114
+ * @v ll_addr		Link-layer address to fill in
115
+ * @ret rc		Return status code
116
+ */
117
+static int eth_mc_hash ( unsigned int af, const void *net_addr,
118
+			 void *ll_addr ) {
119
+	const uint8_t *net_addr_bytes = net_addr;
120
+	uint8_t *ll_addr_bytes = ll_addr;
121
+
122
+	switch ( af ) {
123
+	case AF_INET:
124
+		ll_addr_bytes[0] = 0x01;
125
+		ll_addr_bytes[1] = 0x00;
126
+		ll_addr_bytes[2] = 0x5e;
127
+		ll_addr_bytes[3] = net_addr_bytes[1] & 0x7f;
128
+		ll_addr_bytes[4] = net_addr_bytes[2];
129
+		ll_addr_bytes[5] = net_addr_bytes[3];
130
+	default:
131
+		return -ENOTSUP;
132
+	}
133
+}
134
+
108
 /** Ethernet protocol */
135
 /** Ethernet protocol */
109
 struct ll_protocol ethernet_protocol __ll_protocol = {
136
 struct ll_protocol ethernet_protocol __ll_protocol = {
110
 	.name		= "Ethernet",
137
 	.name		= "Ethernet",
115
 	.push		= eth_push,
142
 	.push		= eth_push,
116
 	.pull		= eth_pull,
143
 	.pull		= eth_pull,
117
 	.ntoa		= eth_ntoa,
144
 	.ntoa		= eth_ntoa,
145
+	.mc_hash	= eth_mc_hash,
118
 };
146
 };

+ 1
- 12
src/net/ipv4.c View File

266
 static int ipv4_ll_addr ( struct in_addr dest, struct in_addr src,
266
 static int ipv4_ll_addr ( struct in_addr dest, struct in_addr src,
267
 			  struct net_device *netdev, uint8_t *ll_dest ) {
267
 			  struct net_device *netdev, uint8_t *ll_dest ) {
268
 	struct ll_protocol *ll_protocol = netdev->ll_protocol;
268
 	struct ll_protocol *ll_protocol = netdev->ll_protocol;
269
-	uint8_t *dest_bytes = ( ( uint8_t * ) &dest );
270
 
269
 
271
 	if ( dest.s_addr == INADDR_BROADCAST ) {
270
 	if ( dest.s_addr == INADDR_BROADCAST ) {
272
 		/* Broadcast address */
271
 		/* Broadcast address */
274
 			 ll_protocol->ll_addr_len );
273
 			 ll_protocol->ll_addr_len );
275
 		return 0;
274
 		return 0;
276
 	} else if ( IN_MULTICAST ( ntohl ( dest.s_addr ) ) ) {
275
 	} else if ( IN_MULTICAST ( ntohl ( dest.s_addr ) ) ) {
277
-		/* Special case: IPv4 multicast over Ethernet.	This
278
-		 * code may need to be generalised once we find out
279
-		 * what happens for other link layers.
280
-		 */
281
-		ll_dest[0] = 0x01;
282
-		ll_dest[1] = 0x00;
283
-		ll_dest[2] = 0x5e;
284
-		ll_dest[3] = dest_bytes[1] & 0x7f;
285
-		ll_dest[4] = dest_bytes[2];
286
-		ll_dest[5] = dest_bytes[3];
287
-		return 0;
276
+		return ll_protocol->mc_hash ( AF_INET, &dest, ll_dest );
288
 	} else {
277
 	} else {
289
 		/* Unicast address: resolve via ARP */
278
 		/* Unicast address: resolve via ARP */
290
 		return arp_resolve ( netdev, &ipv4_protocol, &dest,
279
 		return arp_resolve ( netdev, &ipv4_protocol, &dest,

Loading…
Cancel
Save