xref: /netbsd-src/external/mpl/dhcp/dist/common/ethernet.c (revision f407d9293b6650aa8c33d6a995f797bb6aaefd90)
1 /*	$NetBSD: ethernet.c,v 1.3 2022/04/03 01:10:58 christos Exp $	*/
2 
3 /* ethernet.c
4 
5    Packet assembly code, originally contributed by Archie Cobbs. */
6 
7 /*
8  * Copyright (C) 2004-2022 Internet Systems Consortium, Inc. ("ISC")
9  * Copyright (c) 1996-2003 by Internet Software Consortium
10  *
11  * This Source Code Form is subject to the terms of the Mozilla Public
12  * License, v. 2.0. If a copy of the MPL was not distributed with this
13  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
14  *
15  * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
16  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
17  * MERCHANTABILITY AND FITNESS.  IN NO EVENT SHALL ISC BE LIABLE FOR
18  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
19  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
20  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
21  * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
22  *
23  *   Internet Systems Consortium, Inc.
24  *   PO Box 360
25  *   Newmarket, NH 03857 USA
26  *   <info@isc.org>
27  *   https://www.isc.org/
28  *
29  */
30 
31 #include <sys/cdefs.h>
32 __RCSID("$NetBSD: ethernet.c,v 1.3 2022/04/03 01:10:58 christos Exp $");
33 
34 #include "dhcpd.h"
35 
36 #if defined (PACKET_ASSEMBLY) || defined (PACKET_DECODING)
37 #include "includes/netinet/if_ether.h"
38 #endif /* PACKET_ASSEMBLY || PACKET_DECODING */
39 
40 #if defined (PACKET_ASSEMBLY)
41 /* Assemble an hardware header... */
42 
assemble_ethernet_header(interface,buf,bufix,to)43 void assemble_ethernet_header (interface, buf, bufix, to)
44 	struct interface_info *interface;
45 	unsigned char *buf;
46 	unsigned *bufix;
47 	struct hardware *to;
48 {
49 	struct isc_ether_header eh;
50 
51 	if (to && to -> hlen == 7) /* XXX */
52 		memcpy (eh.ether_dhost, &to -> hbuf [1],
53 			sizeof eh.ether_dhost);
54 	else
55 		memset (eh.ether_dhost, 0xff, sizeof (eh.ether_dhost));
56 	if (interface -> hw_address.hlen - 1 == sizeof (eh.ether_shost))
57 		memcpy (eh.ether_shost, &interface -> hw_address.hbuf [1],
58 			sizeof (eh.ether_shost));
59 	else
60 		memset (eh.ether_shost, 0x00, sizeof (eh.ether_shost));
61 
62 	eh.ether_type = htons (ETHERTYPE_IP);
63 
64 	memcpy (&buf [*bufix], &eh, ETHER_HEADER_SIZE);
65 	*bufix += ETHER_HEADER_SIZE;
66 }
67 #endif /* PACKET_ASSEMBLY */
68 
69 #ifdef PACKET_DECODING
70 /* Decode a hardware header... */
71 
decode_ethernet_header(interface,buf,bufix,from)72 ssize_t decode_ethernet_header (interface, buf, bufix, from)
73      struct interface_info *interface;
74      unsigned char *buf;
75      unsigned bufix;
76      struct hardware *from;
77 {
78   struct isc_ether_header eh;
79 
80   memcpy (&eh, buf + bufix, ETHER_HEADER_SIZE);
81 
82 #ifdef USERLAND_FILTER
83   if (ntohs (eh.ether_type) != ETHERTYPE_IP)
84 	  return -1;
85 #endif
86   memcpy (&from -> hbuf [1], eh.ether_shost, sizeof (eh.ether_shost));
87   from -> hbuf [0] = ARPHRD_ETHER;
88   from -> hlen = (sizeof eh.ether_shost) + 1;
89 
90   return ETHER_HEADER_SIZE;
91 }
92 #endif /* PACKET_DECODING */
93