xref: /linux/net/ethernet/eth.c (revision 36ec807b627b4c0a0a382f0ae48eac7187d14b2b)
12874c5fdSThomas Gleixner // SPDX-License-Identifier: GPL-2.0-or-later
21da177e4SLinus Torvalds /*
31da177e4SLinus Torvalds  * INET		An implementation of the TCP/IP protocol suite for the LINUX
41da177e4SLinus Torvalds  *		operating system.  INET is implemented using the  BSD Socket
51da177e4SLinus Torvalds  *		interface as the means of communication with the user level.
61da177e4SLinus Torvalds  *
71da177e4SLinus Torvalds  *		Ethernet-type device handling.
81da177e4SLinus Torvalds  *
91da177e4SLinus Torvalds  * Version:	@(#)eth.c	1.0.7	05/25/93
101da177e4SLinus Torvalds  *
1102c30a84SJesper Juhl  * Authors:	Ross Biro
121da177e4SLinus Torvalds  *		Fred N. van Kempen, <waltje@uWalt.NL.Mugnet.ORG>
131da177e4SLinus Torvalds  *		Mark Evans, <evansmp@uhura.aston.ac.uk>
141da177e4SLinus Torvalds  *		Florian  La Roche, <rzsfl@rz.uni-sb.de>
151da177e4SLinus Torvalds  *		Alan Cox, <gw4pts@gw4pts.ampr.org>
161da177e4SLinus Torvalds  *
171da177e4SLinus Torvalds  * Fixes:
181da177e4SLinus Torvalds  *		Mr Linux	: Arp problems
191da177e4SLinus Torvalds  *		Alan Cox	: Generic queue tidyup (very tiny here)
201da177e4SLinus Torvalds  *		Alan Cox	: eth_header ntohs should be htons
211da177e4SLinus Torvalds  *		Alan Cox	: eth_rebuild_header missing an htons and
221da177e4SLinus Torvalds  *				  minor other things.
231da177e4SLinus Torvalds  *		Tegge		: Arp bug fixes.
241da177e4SLinus Torvalds  *		Florian		: Removed many unnecessary functions, code cleanup
251da177e4SLinus Torvalds  *				  and changes for new arp and skbuff.
261da177e4SLinus Torvalds  *		Alan Cox	: Redid header building to reflect new format.
271da177e4SLinus Torvalds  *		Alan Cox	: ARP only when compiled with CONFIG_INET
281da177e4SLinus Torvalds  *		Greg Page	: 802.2 and SNAP stuff.
291da177e4SLinus Torvalds  *		Alan Cox	: MAC layer pointers/new format.
301da177e4SLinus Torvalds  *		Paul Gortmaker	: eth_copy_and_sum shouldn't csum padding.
311da177e4SLinus Torvalds  *		Alan Cox	: Protect against forwarding explosions with
321da177e4SLinus Torvalds  *				  older network drivers and IFF_ALLMULTI.
331da177e4SLinus Torvalds  *	Christer Weinigel	: Better rebuild header message.
341da177e4SLinus Torvalds  *             Andrew Morton    : 26Feb01: kill ether_setup() - use netdev_boot_setup().
351da177e4SLinus Torvalds  */
361da177e4SLinus Torvalds #include <linux/module.h>
371da177e4SLinus Torvalds #include <linux/types.h>
381da177e4SLinus Torvalds #include <linux/kernel.h>
391da177e4SLinus Torvalds #include <linux/string.h>
401da177e4SLinus Torvalds #include <linux/mm.h>
411da177e4SLinus Torvalds #include <linux/socket.h>
421da177e4SLinus Torvalds #include <linux/in.h>
431da177e4SLinus Torvalds #include <linux/inet.h>
441da177e4SLinus Torvalds #include <linux/ip.h>
451da177e4SLinus Torvalds #include <linux/netdevice.h>
460e839df9SBartosz Golaszewski #include <linux/nvmem-consumer.h>
471da177e4SLinus Torvalds #include <linux/etherdevice.h>
481da177e4SLinus Torvalds #include <linux/skbuff.h>
491da177e4SLinus Torvalds #include <linux/errno.h>
501da177e4SLinus Torvalds #include <linux/init.h>
5146f25dffSKris Katterjohn #include <linux/if_ether.h>
52c7f5d105SDavid S. Miller #include <linux/of_net.h>
53c7f5d105SDavid S. Miller #include <linux/pci.h>
54433baf07SJakub Kicinski #include <linux/property.h>
551da177e4SLinus Torvalds #include <net/dst.h>
561da177e4SLinus Torvalds #include <net/arp.h>
571da177e4SLinus Torvalds #include <net/sock.h>
581da177e4SLinus Torvalds #include <net/ipv6.h>
591da177e4SLinus Torvalds #include <net/ip.h>
60cf85d08fSLennert Buytenhek #include <net/dsa.h>
6110b89ee4SJiri Pirko #include <net/flow_dissector.h>
625588796eSAlexander Lobakin #include <net/gro.h>
63118a7b0eSAvinash Kumar #include <linux/uaccess.h>
64d0a81f67SJesper Dangaard Brouer #include <net/pkt_sched.h>
651da177e4SLinus Torvalds 
66d3e01f71SStephen Hemminger /**
67d3e01f71SStephen Hemminger  * eth_header - create the Ethernet header
68d3e01f71SStephen Hemminger  * @skb:	buffer to alter
69d3e01f71SStephen Hemminger  * @dev:	source device
70d3e01f71SStephen Hemminger  * @type:	Ethernet type field
71d3e01f71SStephen Hemminger  * @daddr: destination address (NULL leave destination address)
72d3e01f71SStephen Hemminger  * @saddr: source address (NULL use device source address)
73d3e01f71SStephen Hemminger  * @len:   packet length (<= skb->len)
741da177e4SLinus Torvalds  *
75d3e01f71SStephen Hemminger  *
76bf9ae538SOctavian Purdila  * Set the protocol type. For a packet of type ETH_P_802_3/2 we put the length
77bf9ae538SOctavian Purdila  * in here instead.
781da177e4SLinus Torvalds  */
793b04dddeSStephen Hemminger int eth_header(struct sk_buff *skb, struct net_device *dev,
803b04dddeSStephen Hemminger 	       unsigned short type,
8195c96174SEric Dumazet 	       const void *daddr, const void *saddr, unsigned int len)
821da177e4SLinus Torvalds {
83d58ff351SJohannes Berg 	struct ethhdr *eth = skb_push(skb, ETH_HLEN);
841da177e4SLinus Torvalds 
85bf9ae538SOctavian Purdila 	if (type != ETH_P_802_3 && type != ETH_P_802_2)
861da177e4SLinus Torvalds 		eth->h_proto = htons(type);
871da177e4SLinus Torvalds 	else
881da177e4SLinus Torvalds 		eth->h_proto = htons(len);
891da177e4SLinus Torvalds 
901da177e4SLinus Torvalds 	/*
911da177e4SLinus Torvalds 	 *      Set the source hardware address.
921da177e4SLinus Torvalds 	 */
931da177e4SLinus Torvalds 
94ff593c59SDenis Vlasenko 	if (!saddr)
95ff593c59SDenis Vlasenko 		saddr = dev->dev_addr;
9623f1f4efSStephen Hemminger 	memcpy(eth->h_source, saddr, ETH_ALEN);
971da177e4SLinus Torvalds 
982e4ca75bSStephen Hemminger 	if (daddr) {
9923f1f4efSStephen Hemminger 		memcpy(eth->h_dest, daddr, ETH_ALEN);
100f8d0e3f1SJamal Hadi Salim 		return ETH_HLEN;
101f8d0e3f1SJamal Hadi Salim 	}
102f8d0e3f1SJamal Hadi Salim 
1031da177e4SLinus Torvalds 	/*
1041da177e4SLinus Torvalds 	 *      Anyway, the loopback-device should never use this function...
1051da177e4SLinus Torvalds 	 */
1061da177e4SLinus Torvalds 
1072e4ca75bSStephen Hemminger 	if (dev->flags & (IFF_LOOPBACK | IFF_NOARP)) {
108afc130ddSJoe Perches 		eth_zero_addr(eth->h_dest);
1091da177e4SLinus Torvalds 		return ETH_HLEN;
1101da177e4SLinus Torvalds 	}
1111da177e4SLinus Torvalds 
1121da177e4SLinus Torvalds 	return -ETH_HLEN;
1131da177e4SLinus Torvalds }
1143b04dddeSStephen Hemminger EXPORT_SYMBOL(eth_header);
1151da177e4SLinus Torvalds 
116d3e01f71SStephen Hemminger /**
117ecea4991SMasanari Iida  * eth_get_headlen - determine the length of header for an ethernet frame
118c43f1255SStanislav Fomichev  * @dev: pointer to network device
11956193d1bSAlexander Duyck  * @data: pointer to start of frame
12056193d1bSAlexander Duyck  * @len: total length of frame
12156193d1bSAlexander Duyck  *
12256193d1bSAlexander Duyck  * Make a best effort attempt to pull the length for all of the headers for
12356193d1bSAlexander Duyck  * a given frame in a linear buffer.
12456193d1bSAlexander Duyck  */
12559753ce8SAlexander Lobakin u32 eth_get_headlen(const struct net_device *dev, const void *data, u32 len)
12656193d1bSAlexander Duyck {
127d975ddd6SAlexander Duyck 	const unsigned int flags = FLOW_DISSECTOR_F_PARSE_1ST_FRAG;
12856193d1bSAlexander Duyck 	const struct ethhdr *eth = (const struct ethhdr *)data;
12972a338bcSPaolo Abeni 	struct flow_keys_basic keys;
13056193d1bSAlexander Duyck 
13156193d1bSAlexander Duyck 	/* this should never happen, but better safe than sorry */
1328a4683a5SJesper Dangaard Brouer 	if (unlikely(len < sizeof(*eth)))
13356193d1bSAlexander Duyck 		return len;
13456193d1bSAlexander Duyck 
13556193d1bSAlexander Duyck 	/* parse any remaining L2/L3 headers, check for L4 */
136c43f1255SStanislav Fomichev 	if (!skb_flow_dissect_flow_keys_basic(dev_net(dev), NULL, &keys, data,
1373cbf4ffbSStanislav Fomichev 					      eth->h_proto, sizeof(*eth),
1383cbf4ffbSStanislav Fomichev 					      len, flags))
139c3f83241STom Herbert 		return max_t(u32, keys.control.thoff, sizeof(*eth));
14056193d1bSAlexander Duyck 
14156193d1bSAlexander Duyck 	/* parse for any L4 headers */
14256193d1bSAlexander Duyck 	return min_t(u32, __skb_get_poff(NULL, data, &keys, len), len);
14356193d1bSAlexander Duyck }
14456193d1bSAlexander Duyck EXPORT_SYMBOL(eth_get_headlen);
14556193d1bSAlexander Duyck 
14656193d1bSAlexander Duyck /**
147d3e01f71SStephen Hemminger  * eth_type_trans - determine the packet's protocol ID.
148d3e01f71SStephen Hemminger  * @skb: received socket data
149d3e01f71SStephen Hemminger  * @dev: receiving network device
150d3e01f71SStephen Hemminger  *
151d3e01f71SStephen Hemminger  * The rule here is that we
1521da177e4SLinus Torvalds  * assume 802.3 if the type field is short enough to be a length.
1531da177e4SLinus Torvalds  * This is normal practice and works for any 'now in use' protocol.
1541da177e4SLinus Torvalds  */
155ab611487SAlexey Dobriyan __be16 eth_type_trans(struct sk_buff *skb, struct net_device *dev)
1561da177e4SLinus Torvalds {
1570864c158SEric Dumazet 	unsigned short _service_access_point;
1580864c158SEric Dumazet 	const unsigned short *sap;
1590864c158SEric Dumazet 	const struct ethhdr *eth;
1601da177e4SLinus Torvalds 
1614c13eb66SArnaldo Carvalho de Melo 	skb->dev = dev;
162459a98edSArnaldo Carvalho de Melo 	skb_reset_mac_header(skb);
163610986e7SAlexander Duyck 
164*3998d184SDaniel Borkmann 	eth = eth_skb_pull_mac(skb);
1656e159fd6SRahul Rameshbabu 	eth_skb_pkt_type(skb, dev);
1661da177e4SLinus Torvalds 
167cf85d08fSLennert Buytenhek 	/*
168cf85d08fSLennert Buytenhek 	 * Some variants of DSA tagging don't have an ethertype field
169cf85d08fSLennert Buytenhek 	 * at all, so we check here whether one of those tagging
170cf85d08fSLennert Buytenhek 	 * variants has been configured on the receiving interface,
171cf85d08fSLennert Buytenhek 	 * and if so, set skb->protocol without looking at the packet.
172cf85d08fSLennert Buytenhek 	 */
173edac6f63SVladimir Oltean 	if (unlikely(netdev_uses_dsa(dev)))
1743e8a72d1SFlorian Fainelli 		return htons(ETH_P_XDSA);
175cf85d08fSLennert Buytenhek 
1762c7a88c2SAlexander Duyck 	if (likely(eth_proto_is_802_3(eth->h_proto)))
1771da177e4SLinus Torvalds 		return eth->h_proto;
1781da177e4SLinus Torvalds 
1791da177e4SLinus Torvalds 	/*
1801da177e4SLinus Torvalds 	 *      This is a magic hack to spot IPX packets. Older Novell breaks
1811da177e4SLinus Torvalds 	 *      the protocol design and runs IPX over 802.3 without an 802.2 LLC
1821da177e4SLinus Torvalds 	 *      layer. We look for FFFF which isn't a used 802.2 SSAP/DSAP. This
1831da177e4SLinus Torvalds 	 *      won't work for fault tolerant netware but does for the rest.
1841da177e4SLinus Torvalds 	 */
1850864c158SEric Dumazet 	sap = skb_header_pointer(skb, 0, sizeof(*sap), &_service_access_point);
1860864c158SEric Dumazet 	if (sap && *sap == 0xFFFF)
1871da177e4SLinus Torvalds 		return htons(ETH_P_802_3);
1881da177e4SLinus Torvalds 
1891da177e4SLinus Torvalds 	/*
1901da177e4SLinus Torvalds 	 *      Real 802.2 LLC
1911da177e4SLinus Torvalds 	 */
1921da177e4SLinus Torvalds 	return htons(ETH_P_802_2);
1931da177e4SLinus Torvalds }
1942e4ca75bSStephen Hemminger EXPORT_SYMBOL(eth_type_trans);
1951da177e4SLinus Torvalds 
196d3e01f71SStephen Hemminger /**
197d3e01f71SStephen Hemminger  * eth_header_parse - extract hardware address from packet
198d3e01f71SStephen Hemminger  * @skb: packet to extract header from
199d3e01f71SStephen Hemminger  * @haddr: destination buffer
200d3e01f71SStephen Hemminger  */
2013b04dddeSStephen Hemminger int eth_header_parse(const struct sk_buff *skb, unsigned char *haddr)
2021da177e4SLinus Torvalds {
203b95cce35SStephen Hemminger 	const struct ethhdr *eth = eth_hdr(skb);
2041da177e4SLinus Torvalds 	memcpy(haddr, eth->h_source, ETH_ALEN);
2051da177e4SLinus Torvalds 	return ETH_ALEN;
2061da177e4SLinus Torvalds }
2073b04dddeSStephen Hemminger EXPORT_SYMBOL(eth_header_parse);
2081da177e4SLinus Torvalds 
209d3e01f71SStephen Hemminger /**
210d3e01f71SStephen Hemminger  * eth_header_cache - fill cache entry from neighbour
211d3e01f71SStephen Hemminger  * @neigh: source neighbour
212d3e01f71SStephen Hemminger  * @hh: destination cache entry
21348daec03SRandy Dunlap  * @type: Ethernet type field
2142c53040fSBen Hutchings  *
215d3e01f71SStephen Hemminger  * Create an Ethernet header template from the neighbour.
216d3e01f71SStephen Hemminger  */
217e69dd336SDavid S. Miller int eth_header_cache(const struct neighbour *neigh, struct hh_cache *hh, __be16 type)
2181da177e4SLinus Torvalds {
2191da177e4SLinus Torvalds 	struct ethhdr *eth;
2203b04dddeSStephen Hemminger 	const struct net_device *dev = neigh->dev;
2211da177e4SLinus Torvalds 
2221da177e4SLinus Torvalds 	eth = (struct ethhdr *)
2231da177e4SLinus Torvalds 	    (((u8 *) hh->hh_data) + (HH_DATA_OFF(sizeof(*eth))));
2241da177e4SLinus Torvalds 
225f576e24fSYOSHIFUJI Hideaki 	if (type == htons(ETH_P_802_3))
2261da177e4SLinus Torvalds 		return -1;
2271da177e4SLinus Torvalds 
2281da177e4SLinus Torvalds 	eth->h_proto = type;
22923f1f4efSStephen Hemminger 	memcpy(eth->h_source, dev->dev_addr, ETH_ALEN);
23023f1f4efSStephen Hemminger 	memcpy(eth->h_dest, neigh->ha, ETH_ALEN);
231c305c6aeSEric Dumazet 
232c305c6aeSEric Dumazet 	/* Pairs with READ_ONCE() in neigh_resolve_output(),
233c305c6aeSEric Dumazet 	 * neigh_hh_output() and neigh_update_hhs().
234c305c6aeSEric Dumazet 	 */
235c305c6aeSEric Dumazet 	smp_store_release(&hh->hh_len, ETH_HLEN);
236c305c6aeSEric Dumazet 
2371da177e4SLinus Torvalds 	return 0;
2381da177e4SLinus Torvalds }
2393b04dddeSStephen Hemminger EXPORT_SYMBOL(eth_header_cache);
2401da177e4SLinus Torvalds 
241d3e01f71SStephen Hemminger /**
242d3e01f71SStephen Hemminger  * eth_header_cache_update - update cache entry
243d3e01f71SStephen Hemminger  * @hh: destination cache entry
244d3e01f71SStephen Hemminger  * @dev: network device
245d3e01f71SStephen Hemminger  * @haddr: new hardware address
246d3e01f71SStephen Hemminger  *
2471da177e4SLinus Torvalds  * Called by Address Resolution module to notify changes in address.
2481da177e4SLinus Torvalds  */
2493b04dddeSStephen Hemminger void eth_header_cache_update(struct hh_cache *hh,
2503b04dddeSStephen Hemminger 			     const struct net_device *dev,
2513b04dddeSStephen Hemminger 			     const unsigned char *haddr)
2521da177e4SLinus Torvalds {
2531da177e4SLinus Torvalds 	memcpy(((u8 *) hh->hh_data) + HH_DATA_OFF(sizeof(struct ethhdr)),
25423f1f4efSStephen Hemminger 	       haddr, ETH_ALEN);
2551da177e4SLinus Torvalds }
2563b04dddeSStephen Hemminger EXPORT_SYMBOL(eth_header_cache_update);
2571da177e4SLinus Torvalds 
258d3e01f71SStephen Hemminger /**
259c1639be9SMauro Carvalho Chehab  * eth_header_parse_protocol - extract protocol from L2 header
260ace53b2eSMaxim Mikityanskiy  * @skb: packet to extract protocol from
261ace53b2eSMaxim Mikityanskiy  */
262ace53b2eSMaxim Mikityanskiy __be16 eth_header_parse_protocol(const struct sk_buff *skb)
263ace53b2eSMaxim Mikityanskiy {
264ace53b2eSMaxim Mikityanskiy 	const struct ethhdr *eth = eth_hdr(skb);
265ace53b2eSMaxim Mikityanskiy 
266ace53b2eSMaxim Mikityanskiy 	return eth->h_proto;
267ace53b2eSMaxim Mikityanskiy }
268ace53b2eSMaxim Mikityanskiy EXPORT_SYMBOL(eth_header_parse_protocol);
269ace53b2eSMaxim Mikityanskiy 
270ace53b2eSMaxim Mikityanskiy /**
271fa0879e3SStefan Hajnoczi  * eth_prepare_mac_addr_change - prepare for mac change
272fa0879e3SStefan Hajnoczi  * @dev: network device
273fa0879e3SStefan Hajnoczi  * @p: socket address
274fa0879e3SStefan Hajnoczi  */
275fa0879e3SStefan Hajnoczi int eth_prepare_mac_addr_change(struct net_device *dev, void *p)
276fa0879e3SStefan Hajnoczi {
277fa0879e3SStefan Hajnoczi 	struct sockaddr *addr = p;
278fa0879e3SStefan Hajnoczi 
279fa0879e3SStefan Hajnoczi 	if (!(dev->priv_flags & IFF_LIVE_ADDR_CHANGE) && netif_running(dev))
280fa0879e3SStefan Hajnoczi 		return -EBUSY;
281fa0879e3SStefan Hajnoczi 	if (!is_valid_ether_addr(addr->sa_data))
282fa0879e3SStefan Hajnoczi 		return -EADDRNOTAVAIL;
283fa0879e3SStefan Hajnoczi 	return 0;
284fa0879e3SStefan Hajnoczi }
285fa0879e3SStefan Hajnoczi EXPORT_SYMBOL(eth_prepare_mac_addr_change);
286fa0879e3SStefan Hajnoczi 
287fa0879e3SStefan Hajnoczi /**
288fa0879e3SStefan Hajnoczi  * eth_commit_mac_addr_change - commit mac change
289fa0879e3SStefan Hajnoczi  * @dev: network device
290fa0879e3SStefan Hajnoczi  * @p: socket address
291fa0879e3SStefan Hajnoczi  */
292fa0879e3SStefan Hajnoczi void eth_commit_mac_addr_change(struct net_device *dev, void *p)
293fa0879e3SStefan Hajnoczi {
294fa0879e3SStefan Hajnoczi 	struct sockaddr *addr = p;
295fa0879e3SStefan Hajnoczi 
296a96d317fSJakub Kicinski 	eth_hw_addr_set(dev, addr->sa_data);
297fa0879e3SStefan Hajnoczi }
298fa0879e3SStefan Hajnoczi EXPORT_SYMBOL(eth_commit_mac_addr_change);
299fa0879e3SStefan Hajnoczi 
300fa0879e3SStefan Hajnoczi /**
301d3e01f71SStephen Hemminger  * eth_mac_addr - set new Ethernet hardware address
302d3e01f71SStephen Hemminger  * @dev: network device
303d3e01f71SStephen Hemminger  * @p: socket address
3042c53040fSBen Hutchings  *
305d3e01f71SStephen Hemminger  * Change hardware address of device.
306d3e01f71SStephen Hemminger  *
307d3e01f71SStephen Hemminger  * This doesn't change hardware matching, so needs to be overridden
308d3e01f71SStephen Hemminger  * for most real devices.
309d3e01f71SStephen Hemminger  */
310ccad637bSStephen Hemminger int eth_mac_addr(struct net_device *dev, void *p)
3111da177e4SLinus Torvalds {
312fa0879e3SStefan Hajnoczi 	int ret;
31371bffe55SPatrick McHardy 
314fa0879e3SStefan Hajnoczi 	ret = eth_prepare_mac_addr_change(dev, p);
315fa0879e3SStefan Hajnoczi 	if (ret < 0)
316fa0879e3SStefan Hajnoczi 		return ret;
317fa0879e3SStefan Hajnoczi 	eth_commit_mac_addr_change(dev, p);
3181da177e4SLinus Torvalds 	return 0;
3191da177e4SLinus Torvalds }
320ccad637bSStephen Hemminger EXPORT_SYMBOL(eth_mac_addr);
3211da177e4SLinus Torvalds 
322ccad637bSStephen Hemminger int eth_validate_addr(struct net_device *dev)
323bada339bSJeff Garzik {
324bada339bSJeff Garzik 	if (!is_valid_ether_addr(dev->dev_addr))
3252ed9926eSPatrick McHardy 		return -EADDRNOTAVAIL;
326bada339bSJeff Garzik 
327bada339bSJeff Garzik 	return 0;
328bada339bSJeff Garzik }
329ccad637bSStephen Hemminger EXPORT_SYMBOL(eth_validate_addr);
330bada339bSJeff Garzik 
3313b04dddeSStephen Hemminger const struct header_ops eth_header_ops ____cacheline_aligned = {
3323b04dddeSStephen Hemminger 	.create		= eth_header,
3333b04dddeSStephen Hemminger 	.parse		= eth_header_parse,
3343b04dddeSStephen Hemminger 	.cache		= eth_header_cache,
3353b04dddeSStephen Hemminger 	.cache_update	= eth_header_cache_update,
336ace53b2eSMaxim Mikityanskiy 	.parse_protocol	= eth_header_parse_protocol,
3373b04dddeSStephen Hemminger };
3383b04dddeSStephen Hemminger 
339d3e01f71SStephen Hemminger /**
340d3e01f71SStephen Hemminger  * ether_setup - setup Ethernet network device
341d3e01f71SStephen Hemminger  * @dev: network device
3422c53040fSBen Hutchings  *
343d3e01f71SStephen Hemminger  * Fill in the fields of the device structure with Ethernet-generic values.
3441da177e4SLinus Torvalds  */
3451da177e4SLinus Torvalds void ether_setup(struct net_device *dev)
3461da177e4SLinus Torvalds {
3473b04dddeSStephen Hemminger 	dev->header_ops		= &eth_header_ops;
3481da177e4SLinus Torvalds 	dev->type		= ARPHRD_ETHER;
3491da177e4SLinus Torvalds 	dev->hard_header_len 	= ETH_HLEN;
350217e6fa2SWillem de Bruijn 	dev->min_header_len	= ETH_HLEN;
35146f25dffSKris Katterjohn 	dev->mtu		= ETH_DATA_LEN;
352a52ad514SJarod Wilson 	dev->min_mtu		= ETH_MIN_MTU;
353a52ad514SJarod Wilson 	dev->max_mtu		= ETH_DATA_LEN;
3541da177e4SLinus Torvalds 	dev->addr_len		= ETH_ALEN;
355d0a81f67SJesper Dangaard Brouer 	dev->tx_queue_len	= DEFAULT_TX_QUEUE_LEN;
3561da177e4SLinus Torvalds 	dev->flags		= IFF_BROADCAST|IFF_MULTICAST;
35731dda0aeSnhorman 	dev->priv_flags		|= IFF_TX_SKB_SHARING;
3581da177e4SLinus Torvalds 
359afc130ddSJoe Perches 	eth_broadcast_addr(dev->broadcast);
3601da177e4SLinus Torvalds 
3611da177e4SLinus Torvalds }
3621da177e4SLinus Torvalds EXPORT_SYMBOL(ether_setup);
3631da177e4SLinus Torvalds 
3641da177e4SLinus Torvalds /**
36536909ea4STom Herbert  * alloc_etherdev_mqs - Allocates and sets up an Ethernet device
3661da177e4SLinus Torvalds  * @sizeof_priv: Size of additional driver-private structure to be allocated
367d3e01f71SStephen Hemminger  *	for this Ethernet device
36836909ea4STom Herbert  * @txqs: The number of TX queues this device has.
3693806b4f3SRandy Dunlap  * @rxqs: The number of RX queues this device has.
3701da177e4SLinus Torvalds  *
371d3e01f71SStephen Hemminger  * Fill in the fields of the device structure with Ethernet-generic
3721da177e4SLinus Torvalds  * values. Basically does everything except registering the device.
3731da177e4SLinus Torvalds  *
3741da177e4SLinus Torvalds  * Constructs a new net device, complete with a private data area of
375d3e01f71SStephen Hemminger  * size (sizeof_priv).  A 32-byte (not bit) alignment is enforced for
3761da177e4SLinus Torvalds  * this private data area.
3771da177e4SLinus Torvalds  */
3781da177e4SLinus Torvalds 
37936909ea4STom Herbert struct net_device *alloc_etherdev_mqs(int sizeof_priv, unsigned int txqs,
38036909ea4STom Herbert 				      unsigned int rxqs)
3811da177e4SLinus Torvalds {
382e9f656b7SIan Wienand 	return alloc_netdev_mqs(sizeof_priv, "eth%d", NET_NAME_ENUM,
383c835a677STom Gundersen 				ether_setup, txqs, rxqs);
3841da177e4SLinus Torvalds }
38536909ea4STom Herbert EXPORT_SYMBOL(alloc_etherdev_mqs);
3860795af57SJoe Perches 
3877ffc49a6SMichael Chan ssize_t sysfs_format_mac(char *buf, const unsigned char *addr, int len)
3887ffc49a6SMichael Chan {
38916dc16d9Sye xingchen 	return sysfs_emit(buf, "%*phC\n", len, addr);
3907ffc49a6SMichael Chan }
3917ffc49a6SMichael Chan EXPORT_SYMBOL(sysfs_format_mac);
3929b174d88SJesse Gross 
393d4546c25SDavid Miller struct sk_buff *eth_gro_receive(struct list_head *head, struct sk_buff *skb)
3949b174d88SJesse Gross {
3959b174d88SJesse Gross 	const struct packet_offload *ptype;
396d4546c25SDavid Miller 	unsigned int hlen, off_eth;
397d4546c25SDavid Miller 	struct sk_buff *pp = NULL;
398d4546c25SDavid Miller 	struct ethhdr *eh, *eh2;
399d4546c25SDavid Miller 	struct sk_buff *p;
4009b174d88SJesse Gross 	__be16 type;
4019b174d88SJesse Gross 	int flush = 1;
4029b174d88SJesse Gross 
4039b174d88SJesse Gross 	off_eth = skb_gro_offset(skb);
4049b174d88SJesse Gross 	hlen = off_eth + sizeof(*eh);
40535ffb665SRichard Gobert 	eh = skb_gro_header(skb, hlen, off_eth);
4069b174d88SJesse Gross 	if (unlikely(!eh))
4079b174d88SJesse Gross 		goto out;
4089b174d88SJesse Gross 
4099b174d88SJesse Gross 	flush = 0;
4109b174d88SJesse Gross 
411d4546c25SDavid Miller 	list_for_each_entry(p, head, list) {
4129b174d88SJesse Gross 		if (!NAPI_GRO_CB(p)->same_flow)
4139b174d88SJesse Gross 			continue;
4149b174d88SJesse Gross 
4159b174d88SJesse Gross 		eh2 = (struct ethhdr *)(p->data + off_eth);
4169b174d88SJesse Gross 		if (compare_ether_header(eh, eh2)) {
4179b174d88SJesse Gross 			NAPI_GRO_CB(p)->same_flow = 0;
4189b174d88SJesse Gross 			continue;
4199b174d88SJesse Gross 		}
4209b174d88SJesse Gross 	}
4219b174d88SJesse Gross 
4229b174d88SJesse Gross 	type = eh->h_proto;
4239b174d88SJesse Gross 
4249b174d88SJesse Gross 	ptype = gro_find_receive_by_type(type);
4259b174d88SJesse Gross 	if (ptype == NULL) {
4269b174d88SJesse Gross 		flush = 1;
427fc1ca334SEric Dumazet 		goto out;
4289b174d88SJesse Gross 	}
4299b174d88SJesse Gross 
4309b174d88SJesse Gross 	skb_gro_pull(skb, sizeof(*eh));
4319b174d88SJesse Gross 	skb_gro_postpull_rcsum(skb, eh, sizeof(*eh));
4325588796eSAlexander Lobakin 
4335588796eSAlexander Lobakin 	pp = indirect_call_gro_receive_inet(ptype->callbacks.gro_receive,
4345588796eSAlexander Lobakin 					    ipv6_gro_receive, inet_gro_receive,
4355588796eSAlexander Lobakin 					    head, skb);
4369b174d88SJesse Gross 
4379b174d88SJesse Gross out:
4385f114163SSteffen Klassert 	skb_gro_flush_final(skb, pp, flush);
4399b174d88SJesse Gross 
4409b174d88SJesse Gross 	return pp;
4419b174d88SJesse Gross }
4429b174d88SJesse Gross EXPORT_SYMBOL(eth_gro_receive);
4439b174d88SJesse Gross 
4449b174d88SJesse Gross int eth_gro_complete(struct sk_buff *skb, int nhoff)
4459b174d88SJesse Gross {
4469b174d88SJesse Gross 	struct ethhdr *eh = (struct ethhdr *)(skb->data + nhoff);
4479b174d88SJesse Gross 	__be16 type = eh->h_proto;
4489b174d88SJesse Gross 	struct packet_offload *ptype;
4499b174d88SJesse Gross 	int err = -ENOSYS;
4509b174d88SJesse Gross 
4519b174d88SJesse Gross 	if (skb->encapsulation)
4529b174d88SJesse Gross 		skb_set_inner_mac_header(skb, nhoff);
4539b174d88SJesse Gross 
4549b174d88SJesse Gross 	ptype = gro_find_complete_by_type(type);
4559b174d88SJesse Gross 	if (ptype != NULL)
4565588796eSAlexander Lobakin 		err = INDIRECT_CALL_INET(ptype->callbacks.gro_complete,
4575588796eSAlexander Lobakin 					 ipv6_gro_complete, inet_gro_complete,
4585588796eSAlexander Lobakin 					 skb, nhoff + sizeof(*eh));
4599b174d88SJesse Gross 
4609b174d88SJesse Gross 	return err;
4619b174d88SJesse Gross }
4629b174d88SJesse Gross EXPORT_SYMBOL(eth_gro_complete);
4639b174d88SJesse Gross 
4649b174d88SJesse Gross static struct packet_offload eth_packet_offload __read_mostly = {
4659b174d88SJesse Gross 	.type = cpu_to_be16(ETH_P_TEB),
466bdef7de4SDavid S. Miller 	.priority = 10,
4679b174d88SJesse Gross 	.callbacks = {
4689b174d88SJesse Gross 		.gro_receive = eth_gro_receive,
4699b174d88SJesse Gross 		.gro_complete = eth_gro_complete,
4709b174d88SJesse Gross 	},
4719b174d88SJesse Gross };
4729b174d88SJesse Gross 
4739b174d88SJesse Gross static int __init eth_offload_init(void)
4749b174d88SJesse Gross {
4759b174d88SJesse Gross 	dev_add_offload(&eth_packet_offload);
4769b174d88SJesse Gross 
4779b174d88SJesse Gross 	return 0;
4789b174d88SJesse Gross }
4799b174d88SJesse Gross 
4809b174d88SJesse Gross fs_initcall(eth_offload_init);
481c7f5d105SDavid S. Miller 
482c7f5d105SDavid S. Miller unsigned char * __weak arch_get_platform_mac_address(void)
483c7f5d105SDavid S. Miller {
484c7f5d105SDavid S. Miller 	return NULL;
485c7f5d105SDavid S. Miller }
486c7f5d105SDavid S. Miller 
487c7f5d105SDavid S. Miller int eth_platform_get_mac_address(struct device *dev, u8 *mac_addr)
488c7f5d105SDavid S. Miller {
48983216e39SMichael Walle 	unsigned char *addr;
49083216e39SMichael Walle 	int ret;
491c7f5d105SDavid S. Miller 
49283216e39SMichael Walle 	ret = of_get_mac_address(dev->of_node, mac_addr);
49383216e39SMichael Walle 	if (!ret)
49483216e39SMichael Walle 		return 0;
49583216e39SMichael Walle 
496c7f5d105SDavid S. Miller 	addr = arch_get_platform_mac_address();
497c7f5d105SDavid S. Miller 	if (!addr)
498c7f5d105SDavid S. Miller 		return -ENODEV;
499c7f5d105SDavid S. Miller 
500c7f5d105SDavid S. Miller 	ether_addr_copy(mac_addr, addr);
501db4bad07SHeiner Kallweit 
502c7f5d105SDavid S. Miller 	return 0;
503c7f5d105SDavid S. Miller }
504c7f5d105SDavid S. Miller EXPORT_SYMBOL(eth_platform_get_mac_address);
5050e839df9SBartosz Golaszewski 
5060e839df9SBartosz Golaszewski /**
507ba882580SJakub Kicinski  * platform_get_ethdev_address - Set netdev's MAC address from a given device
508ba882580SJakub Kicinski  * @dev:	Pointer to the device
509ba882580SJakub Kicinski  * @netdev:	Pointer to netdev to write the address to
510ba882580SJakub Kicinski  *
511ba882580SJakub Kicinski  * Wrapper around eth_platform_get_mac_address() which writes the address
512ba882580SJakub Kicinski  * directly to netdev->dev_addr.
513ba882580SJakub Kicinski  */
514ba882580SJakub Kicinski int platform_get_ethdev_address(struct device *dev, struct net_device *netdev)
515ba882580SJakub Kicinski {
516ba882580SJakub Kicinski 	u8 addr[ETH_ALEN] __aligned(2);
517ba882580SJakub Kicinski 	int ret;
518ba882580SJakub Kicinski 
519ba882580SJakub Kicinski 	ret = eth_platform_get_mac_address(dev, addr);
520ba882580SJakub Kicinski 	if (!ret)
521ba882580SJakub Kicinski 		eth_hw_addr_set(netdev, addr);
522ba882580SJakub Kicinski 	return ret;
523ba882580SJakub Kicinski }
524ba882580SJakub Kicinski EXPORT_SYMBOL(platform_get_ethdev_address);
525ba882580SJakub Kicinski 
526ba882580SJakub Kicinski /**
527c1639be9SMauro Carvalho Chehab  * nvmem_get_mac_address - Obtain the MAC address from an nvmem cell named
528c1639be9SMauro Carvalho Chehab  * 'mac-address' associated with given device.
5290e839df9SBartosz Golaszewski  *
5300e839df9SBartosz Golaszewski  * @dev:	Device with which the mac-address cell is associated.
5310e839df9SBartosz Golaszewski  * @addrbuf:	Buffer to which the MAC address will be copied on success.
5320e839df9SBartosz Golaszewski  *
5330e839df9SBartosz Golaszewski  * Returns 0 on success or a negative error number on failure.
5340e839df9SBartosz Golaszewski  */
5350e839df9SBartosz Golaszewski int nvmem_get_mac_address(struct device *dev, void *addrbuf)
5360e839df9SBartosz Golaszewski {
5370e839df9SBartosz Golaszewski 	struct nvmem_cell *cell;
5380e839df9SBartosz Golaszewski 	const void *mac;
5390e839df9SBartosz Golaszewski 	size_t len;
5400e839df9SBartosz Golaszewski 
5410e839df9SBartosz Golaszewski 	cell = nvmem_cell_get(dev, "mac-address");
5420e839df9SBartosz Golaszewski 	if (IS_ERR(cell))
5430e839df9SBartosz Golaszewski 		return PTR_ERR(cell);
5440e839df9SBartosz Golaszewski 
5450e839df9SBartosz Golaszewski 	mac = nvmem_cell_read(cell, &len);
5460e839df9SBartosz Golaszewski 	nvmem_cell_put(cell);
5470e839df9SBartosz Golaszewski 
5480e839df9SBartosz Golaszewski 	if (IS_ERR(mac))
5490e839df9SBartosz Golaszewski 		return PTR_ERR(mac);
5500e839df9SBartosz Golaszewski 
5510e839df9SBartosz Golaszewski 	if (len != ETH_ALEN || !is_valid_ether_addr(mac)) {
5520e839df9SBartosz Golaszewski 		kfree(mac);
5530e839df9SBartosz Golaszewski 		return -EINVAL;
5540e839df9SBartosz Golaszewski 	}
5550e839df9SBartosz Golaszewski 
5560e839df9SBartosz Golaszewski 	ether_addr_copy(addrbuf, mac);
5570e839df9SBartosz Golaszewski 	kfree(mac);
5580e839df9SBartosz Golaszewski 
5590e839df9SBartosz Golaszewski 	return 0;
5600e839df9SBartosz Golaszewski }
561433baf07SJakub Kicinski 
5628017c4d8SJakub Kicinski static int fwnode_get_mac_addr(struct fwnode_handle *fwnode,
5630a14501eSJakub Kicinski 			       const char *name, char *addr)
564433baf07SJakub Kicinski {
5658017c4d8SJakub Kicinski 	int ret;
566433baf07SJakub Kicinski 
5670a14501eSJakub Kicinski 	ret = fwnode_property_read_u8_array(fwnode, name, addr, ETH_ALEN);
5688017c4d8SJakub Kicinski 	if (ret)
5698017c4d8SJakub Kicinski 		return ret;
5708017c4d8SJakub Kicinski 
5718017c4d8SJakub Kicinski 	if (!is_valid_ether_addr(addr))
5728017c4d8SJakub Kicinski 		return -EINVAL;
5738017c4d8SJakub Kicinski 	return 0;
574433baf07SJakub Kicinski }
575433baf07SJakub Kicinski 
576433baf07SJakub Kicinski /**
577433baf07SJakub Kicinski  * fwnode_get_mac_address - Get the MAC from the firmware node
578433baf07SJakub Kicinski  * @fwnode:	Pointer to the firmware node
579433baf07SJakub Kicinski  * @addr:	Address of buffer to store the MAC in
580433baf07SJakub Kicinski  *
581433baf07SJakub Kicinski  * Search the firmware node for the best MAC address to use.  'mac-address' is
582433baf07SJakub Kicinski  * checked first, because that is supposed to contain to "most recent" MAC
583433baf07SJakub Kicinski  * address. If that isn't set, then 'local-mac-address' is checked next,
584433baf07SJakub Kicinski  * because that is the default address.  If that isn't set, then the obsolete
585433baf07SJakub Kicinski  * 'address' is checked, just in case we're using an old device tree.
586433baf07SJakub Kicinski  *
587433baf07SJakub Kicinski  * Note that the 'address' property is supposed to contain a virtual address of
588433baf07SJakub Kicinski  * the register set, but some DTS files have redefined that property to be the
589433baf07SJakub Kicinski  * MAC address.
590433baf07SJakub Kicinski  *
591433baf07SJakub Kicinski  * All-zero MAC addresses are rejected, because those could be properties that
592433baf07SJakub Kicinski  * exist in the firmware tables, but were not updated by the firmware.  For
593433baf07SJakub Kicinski  * example, the DTS could define 'mac-address' and 'local-mac-address', with
594433baf07SJakub Kicinski  * zero MAC addresses.  Some older U-Boots only initialized 'local-mac-address'.
595433baf07SJakub Kicinski  * In this case, the real MAC is in 'local-mac-address', and 'mac-address'
596433baf07SJakub Kicinski  * exists but is all zeros.
597433baf07SJakub Kicinski  */
5980a14501eSJakub Kicinski int fwnode_get_mac_address(struct fwnode_handle *fwnode, char *addr)
599433baf07SJakub Kicinski {
6000a14501eSJakub Kicinski 	if (!fwnode_get_mac_addr(fwnode, "mac-address", addr) ||
6010a14501eSJakub Kicinski 	    !fwnode_get_mac_addr(fwnode, "local-mac-address", addr) ||
6020a14501eSJakub Kicinski 	    !fwnode_get_mac_addr(fwnode, "address", addr))
6038017c4d8SJakub Kicinski 		return 0;
604433baf07SJakub Kicinski 
6058017c4d8SJakub Kicinski 	return -ENOENT;
606433baf07SJakub Kicinski }
607433baf07SJakub Kicinski EXPORT_SYMBOL(fwnode_get_mac_address);
608433baf07SJakub Kicinski 
609433baf07SJakub Kicinski /**
610433baf07SJakub Kicinski  * device_get_mac_address - Get the MAC for a given device
611433baf07SJakub Kicinski  * @dev:	Pointer to the device
612433baf07SJakub Kicinski  * @addr:	Address of buffer to store the MAC in
613433baf07SJakub Kicinski  */
6140a14501eSJakub Kicinski int device_get_mac_address(struct device *dev, char *addr)
615433baf07SJakub Kicinski {
6160a14501eSJakub Kicinski 	return fwnode_get_mac_address(dev_fwnode(dev), addr);
617433baf07SJakub Kicinski }
618433baf07SJakub Kicinski EXPORT_SYMBOL(device_get_mac_address);
619d9eb4490SJakub Kicinski 
620d9eb4490SJakub Kicinski /**
621d9eb4490SJakub Kicinski  * device_get_ethdev_address - Set netdev's MAC address from a given device
622d9eb4490SJakub Kicinski  * @dev:	Pointer to the device
623d9eb4490SJakub Kicinski  * @netdev:	Pointer to netdev to write the address to
624d9eb4490SJakub Kicinski  *
625d9eb4490SJakub Kicinski  * Wrapper around device_get_mac_address() which writes the address
626d9eb4490SJakub Kicinski  * directly to netdev->dev_addr.
627d9eb4490SJakub Kicinski  */
628d9eb4490SJakub Kicinski int device_get_ethdev_address(struct device *dev, struct net_device *netdev)
629d9eb4490SJakub Kicinski {
630d9eb4490SJakub Kicinski 	u8 addr[ETH_ALEN];
631d9eb4490SJakub Kicinski 	int ret;
632d9eb4490SJakub Kicinski 
633d9eb4490SJakub Kicinski 	ret = device_get_mac_address(dev, addr);
634d9eb4490SJakub Kicinski 	if (!ret)
635d9eb4490SJakub Kicinski 		eth_hw_addr_set(netdev, addr);
636d9eb4490SJakub Kicinski 	return ret;
637d9eb4490SJakub Kicinski }
638d9eb4490SJakub Kicinski EXPORT_SYMBOL(device_get_ethdev_address);
639