File:  [ELWIX - Embedded LightWeight unIX -] / embedaddon / dhcp / common / raw.c
Revision 1.1.1.1 (vendor branch): download - view: text, annotated - select for diffs - revision graph
Tue Oct 9 09:06:54 2012 UTC (12 years ago) by misho
Branches: dhcp, MAIN
CVS tags: v4_1_R7p0, v4_1_R7, v4_1_R4, HEAD
dhcp 4.1 r7

    1: /* raw.c
    2: 
    3:    BSD raw socket interface code... */
    4: 
    5: /* XXX
    6: 
    7:    It's not clear how this should work, and that lack of clarity is
    8:    terribly detrimental to the NetBSD 1.1 kernel - it crashes and
    9:    burns.
   10: 
   11:    Using raw sockets ought to be a big win over using BPF or something
   12:    like it, because you don't need to deal with the complexities of
   13:    the physical layer, but it appears not to be possible with existing
   14:    raw socket implementations.  This may be worth revisiting in the
   15:    future.  For now, this code can probably be considered a curiosity.
   16:    Sigh. */
   17: 
   18: /*
   19:  * Copyright (c) 2004,2007,2009 by Internet Systems Consortium, Inc. ("ISC")
   20:  * Copyright (c) 1995-2003 by Internet Software Consortium
   21:  *
   22:  * Permission to use, copy, modify, and distribute this software for any
   23:  * purpose with or without fee is hereby granted, provided that the above
   24:  * copyright notice and this permission notice appear in all copies.
   25:  *
   26:  * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
   27:  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
   28:  * MERCHANTABILITY AND FITNESS.  IN NO EVENT SHALL ISC BE LIABLE FOR
   29:  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
   30:  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
   31:  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
   32:  * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
   33:  *
   34:  *   Internet Systems Consortium, Inc.
   35:  *   950 Charter Street
   36:  *   Redwood City, CA 94063
   37:  *   <info@isc.org>
   38:  *   https://www.isc.org/
   39:  *
   40:  * This software has been written for Internet Systems Consortium
   41:  * by Ted Lemon in cooperation with Vixie Enterprises and Nominum, Inc.
   42:  * To learn more about Internet Systems Consortium, see
   43:  * ``https://www.isc.org/''.  To learn more about Vixie Enterprises,
   44:  * see ``http://www.vix.com''.   To learn more about Nominum, Inc., see
   45:  * ``http://www.nominum.com''.
   46:  */
   47: 
   48: #include "dhcpd.h"
   49: 
   50: #if defined (USE_RAW_SEND)
   51: #include <sys/uio.h>
   52: 
   53: /* Generic interface registration routine... */
   54: void if_register_send (info)
   55: 	struct interface_info *info;
   56: {
   57: 	struct sockaddr_in name;
   58: 	int sock;
   59: 	struct socklist *tmp;
   60: 	int flag;
   61: 
   62: 	/* Set up the address we're going to connect to. */
   63: 	name.sin_family = AF_INET;
   64: 	name.sin_port = local_port;
   65: 	name.sin_addr.s_addr = htonl (INADDR_BROADCAST);
   66: 	memset (name.sin_zero, 0, sizeof (name.sin_zero));
   67: 
   68: 	/* List addresses on which we're listening. */
   69:         if (!quiet_interface_discovery)
   70: 		log_info ("Sending on %s, port %d",
   71: 		      piaddr (info -> address), htons (local_port));
   72: 	if ((sock = socket (AF_INET, SOCK_RAW, IPPROTO_RAW)) < 0)
   73: 		log_fatal ("Can't create dhcp socket: %m");
   74: 
   75: 	/* Set the BROADCAST option so that we can broadcast DHCP responses. */
   76: 	flag = 1;
   77: 	if (setsockopt (sock, SOL_SOCKET, SO_BROADCAST,
   78: 			&flag, sizeof flag) < 0)
   79: 		log_fatal ("Can't set SO_BROADCAST option on dhcp socket: %m");
   80: 
   81: 	/* Set the IP_HDRINCL flag so that we can supply our own IP
   82: 	   headers... */
   83: 	if (setsockopt (sock, IPPROTO_IP, IP_HDRINCL, &flag, sizeof flag) < 0)
   84: 		log_fatal ("Can't set IP_HDRINCL flag: %m");
   85: 
   86: 	info -> wfdesc = sock;
   87:         if (!quiet_interface_discovery)
   88: 		log_info ("Sending on   Raw/%s%s%s",
   89: 		      info -> name,
   90: 		      (info -> shared_network ? "/" : ""),
   91: 		      (info -> shared_network ?
   92: 		       info -> shared_network -> name : ""));
   93: }
   94: 
   95: void if_deregister_send (info)
   96: 	struct interface_info *info;
   97: {
   98: 	close (info -> wfdesc);
   99: 	info -> wfdesc = -1;
  100: 
  101:         if (!quiet_interface_discovery)
  102: 		log_info ("Disabling output on Raw/%s%s%s",
  103: 		      info -> name,
  104: 		      (info -> shared_network ? "/" : ""),
  105: 		      (info -> shared_network ?
  106: 		       info -> shared_network -> name : ""));
  107: }
  108: 
  109: size_t send_packet (interface, packet, raw, len, from, to, hto)
  110: 	struct interface_info *interface;
  111: 	struct packet *packet;
  112: 	struct dhcp_packet *raw;
  113: 	size_t len;
  114: 	struct in_addr from;
  115: 	struct sockaddr_in *to;
  116: 	struct hardware *hto;
  117: {
  118: 	unsigned char buf [256];
  119: 	int bufp = 0;
  120: 	struct iovec iov [2];
  121: 	int result;
  122: 
  123: 	/* Assemble the headers... */
  124: 	assemble_udp_ip_header (interface, buf, &bufp, from.s_addr,
  125: 				to -> sin_addr.s_addr, to -> sin_port,
  126: 				(unsigned char *)raw, len);
  127: 
  128: 	/* Fire it off */
  129: 	iov [0].iov_base = (char *)buf;
  130: 	iov [0].iov_len = bufp;
  131: 	iov [1].iov_base = (char *)raw;
  132: 	iov [1].iov_len = len;
  133: 
  134: 	result = writev(interface -> wfdesc, iov, 2);
  135: 	if (result < 0)
  136: 		log_error ("send_packet: %m");
  137: 	return result;
  138: }
  139: #endif /* USE_SOCKET_SEND */

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>