Esempio n. 1
0
        /// <summary>
        ///  Process INFORM message type.
        /// </summary>
        private void DhcpInform(DhcpMessageEventArgs args)
        {
            #region Pre-Processing
            //  Start pre-process validation

            // if the client provided a ServerID option, then it MUST
            // match our configured ServerID, otherwise ignore the request
            InternetAddress serverIdentifier = new InternetAddress(args.RequestOptions.ServerIdentifier);
            //InternetAddress localServerIdentifier = new InternetAddress(((IPEndPoint)_dhcpSocket.LocalEndPoint).Address.GetAddressBytes());
            InternetAddress localServerIdentifier = new InternetAddress(this.InterfaceAddress);
            if (!serverIdentifier.Equals(localServerIdentifier))
            {
                Logger.WriteDebug(this, "Ignoring INFORM message: "
                                  + "Requested ServerId: " + serverIdentifier.ToString()
                                  + " Local ServerId: " + localServerIdentifier.ToString());
                return; // if processing should not continue
            }

            // End pre-Process validation
            #endregion Pre-Processing

            this.SendAck(args);
        }
Esempio n. 2
0
        /// <summary>
        ///  Send response message back to remote client.
        /// </summary>
        private void SendReply(DhcpMessageEventArgs args)
        {
            // set global headers
            args.ResponseMessage.Operation             = OperationCode.BootReply;
            args.ResponseMessage.Hardware              = args.RequestMessage.Hardware;
            args.ResponseMessage.HardwareAddressLength = args.RequestMessage.HardwareAddressLength;
            args.ResponseMessage.SessionId             = args.RequestMessage.SessionId;
            args.ResponseMessage.Flags                 = args.RequestMessage.Flags;
            args.ResponseMessage.RelayAgentAddress     = args.RequestMessage.RelayAgentAddress;
            args.ResponseMessage.ClientHardwareAddress = args.RequestMessage.ClientHardwareAddress;

            if (!StringUtility.IsNullOrEmpty(this._serverName))
            {
                args.ResponseMessage.ServerName = Encoding.UTF8.GetBytes(this._serverName);
            }

            if (!StringUtility.IsNullOrEmpty(this._bootFileName))
            {
                args.ResponseMessage.BootFileName = Encoding.UTF8.GetBytes(this._bootFileName);
            }

            // set global options
            //args.ResponseMessage.AddOption(DhcpOption.ServerIdentifier, ((IPEndPoint)_dhcpSocket.LocalEndPoint).Address.GetAddressBytes());
            args.ResponseMessage.AddOption(DhcpOption.ServerIdentifier, (this.InterfaceAddress.GetAddressBytes()));

            // determin the proper ip address and port for sendto
            InternetAddress relayAgentAddress = args.RequestMessage.RelayAgentAddress;
            InternetAddress clientAddress     = args.RequestMessage.ClientAddress;

            if (!relayAgentAddress.Equals(InternetAddress.Any))
            {
                args.Channel.RemoteEndpoint = new IPEndPoint(relayAgentAddress.ToIPAddress(), Constants.DHCP_SERVICE_PORT);
            }
            else
            {
                if (!clientAddress.Equals(InternetAddress.Any))
                {
                    args.Channel.RemoteEndpoint = new IPEndPoint(clientAddress.ToIPAddress(), Constants.DHCP_CLIENT_PORT);
                }
                else
                {
                    args.Channel.RemoteEndpoint = new IPEndPoint(InternetAddress.Broadcast.ToIPAddress(), Constants.DHCP_CLIENT_PORT);
                }
            }

            try
            {
                args.Channel.SendTo(args.ResponseMessage.ToArray(), args.Channel.RemoteEndpoint);
                Logger.WriteDebug(this, "PACKET with message id " +
                                  args.ResponseMessage.SessionId.ToHexString("0x") + " successfully sent to client endpoint " +
                                  args.Channel.RemoteEndpoint.ToString());

                Logger.WriteDebug(args.ResponseMessage.ToString());

                OnDhcpMessageSent(this, args);
            }
            catch (SocketException ex)
            {
                Logger.WriteError(this, ex.Message + "Socket Error Code: " + ex.ErrorCode.ToString(), ex);
            }
            catch (Exception ex)
            {
                Logger.WriteError(this, "Error Message:" + ex.Message.ToString(), ex);
            }
        }
Esempio n. 3
0
        /// <summary>
        ///  Process INFORM message type.
        /// </summary>
        private void DhcpInform(DhcpMessageEventArgs args)
        {
            #region Pre-Processing
            //  Start pre-process validation

            // if the client provided a ServerID option, then it MUST
            // match our configured ServerID, otherwise ignore the request
            InternetAddress serverIdentifier = new InternetAddress(args.RequestOptions.ServerIdentifier);
            //InternetAddress localServerIdentifier = new InternetAddress(((IPEndPoint)_dhcpSocket.LocalEndPoint).Address.GetAddressBytes());
            InternetAddress localServerIdentifier = new InternetAddress(this.InterfaceAddress);
            if (!serverIdentifier.Equals(localServerIdentifier))
            {
                Logger.WriteDebug(this, "Ignoring INFORM message: "
                    + "Requested ServerId: " + serverIdentifier.ToString()
                    + " Local ServerId: " + localServerIdentifier.ToString());
                return; // if processing should not continue
            }

            // End pre-Process validation
            #endregion Pre-Processing

            this.SendAck(args);
        }
Esempio n. 4
0
        /// <summary>
        ///  Process REQUEST message type.
        /// </summary>
        private void DhcpRequest(DhcpMessageEventArgs args)
        {
            RequestState requestState;

            #region Pre-Processing
            //  Start pre-process validation
            //---------------------------------------------------------------------
            //|              |INIT-REBOOT  |SELECTING    |RENEWING     |REBINDING |
            //---------------------------------------------------------------------
            //|broad/unicast |broadcast    |broadcast    |unicast      |broadcast |
            //|server-ip     |MUST NOT     |MUST         |MUST NOT     |MUST NOT  |
            //|requested-ip  |MUST         |MUST         |MUST NOT     |MUST NOT  |
            //|ciaddr        |zero         |zero         |IP address   |IP address|
            //---------------------------------------------------------------------
            // first determine what KIND of request we are dealing with
            if (args.RequestMessage.ClientAddress.Equals(InternetAddress.Any))
            {
                // the ciAddr MUST be 0.0.0.0 for Init-Reboot and Selecting
                if (args.RequestOptions.AddressRequest == null)
                {
                    // init-reboot MUST NOT have server-id option
                    requestState = RequestState.InitReboot;
                }
                else
                {
                    // selecting MUST have server-id option
                    requestState = RequestState.Selecting;
                }
            }
            else
            {
                // the ciAddr MUST NOT be 0.0.0.0 for Renew and Rebind
                if (!args.RequestMessage.IsBroadcast)
                {
                    // renew is unicast
                    // NOTE: this will not happen if the v4 broadcast interface used at startup,
                    //		 but handling of DHCPv4 renew/rebind is the same anyway
                    requestState = RequestState.Renewing;
                }
                else
                {
                    // rebind is broadcast
                    requestState = RequestState.Rebinding;
                }
            }

            if ((requestState == RequestState.InitReboot) || (requestState == RequestState.Selecting))
            {
                if (args.RequestOptions.AddressRequest == null)
                {
                    Logger.WriteDebug(this, "Ignoring REQUEST " + RequestStateString.GetName(requestState) + " message: Requested IP option is null");
                    return; // if processing should not continue
                }

                if (requestState == RequestState.Selecting)
                {
                    // if the client provided a ServerID option, then it MUST
                    // match our configured ServerID, otherwise ignore the request
                    InternetAddress serverIdentifier = new InternetAddress(args.RequestOptions.ServerIdentifier);
                    //InternetAddress localServerIdentifier = new InternetAddress(((IPEndPoint)_dhcpSocket.LocalEndPoint).Address.GetAddressBytes());
                    InternetAddress localServerIdentifier = new InternetAddress(this.InterfaceAddress);
                    if (!serverIdentifier.Equals(localServerIdentifier))
                    {
                        Logger.WriteDebug(this, "Ignoring REQUEST " + RequestStateString.GetName(requestState) + " message: "
                                          + "Requested ServerId: " + serverIdentifier.ToString()
                                          + " Local ServerId: " + localServerIdentifier.ToString());
                        return; // if processing should not continue
                    }
                }
            }
            else
            {   // type == Renewing or Rebinding
                if (args.RequestOptions.AddressRequest != null)
                {
                    Logger.WriteDebug(this, "Ignoring REQUEST " + RequestStateString.GetName(requestState) + " message: "
                                      + "Requested IP option is not null");
                    return; // if processing should not continue
                }
            }

            //  End pre-process validation
            #endregion Pre-Processing

            Logger.WriteDebug(this, "Processing REQUEST " + RequestStateString.GetName(requestState) + " message");

            //TODO:  should also check for ip on link

            if (args.RequestOptions.AddressRequest != null)
            {
                args.ResponseBinding.Address = new InternetAddress(args.RequestOptions.AddressRequest);
            }

            BindingLease assignment = _bindmgr.GetAssigned(args.ResponseBinding);
            if (assignment == null)
            {
                args.ResponseMessage.AddOption(DhcpOption.DhcpMessage, Encoding.UTF8.GetBytes("No binding available for client"));
                Logger.WriteDebug(this, "REQUEST " + RequestStateString.GetName(requestState) + " message: No binding available for client sending NAK");
                this.SendNak(args);
            }
            else
            {
                this.SendAck(args, assignment);
                this.OnLeaseAcknowledged(this, new DhcpLeaseEventArgs(assignment.Address, assignment));
            }
        }
Esempio n. 5
0
        /// <summary>
        ///  Process REQUEST message type.
        /// </summary>
        private void DhcpRequest(DhcpMessageEventArgs args)
        {
            RequestState requestState;

            #region Pre-Processing
            //  Start pre-process validation
            //---------------------------------------------------------------------
            //|              |INIT-REBOOT  |SELECTING    |RENEWING     |REBINDING |
            //---------------------------------------------------------------------
            //|broad/unicast |broadcast    |broadcast    |unicast      |broadcast |
            //|server-ip     |MUST NOT     |MUST         |MUST NOT     |MUST NOT  |
            //|requested-ip  |MUST         |MUST         |MUST NOT     |MUST NOT  |
            //|ciaddr        |zero         |zero         |IP address   |IP address|
            //---------------------------------------------------------------------
            // first determine what KIND of request we are dealing with
            if (args.RequestMessage.ClientAddress.Equals(InternetAddress.Any))
            {
                // the ciAddr MUST be 0.0.0.0 for Init-Reboot and Selecting
                if (args.RequestOptions.AddressRequest == null)
                {
                    // init-reboot MUST NOT have server-id option
                    requestState = RequestState.InitReboot;
                }
                else
                {
                    // selecting MUST have server-id option
                    requestState = RequestState.Selecting;
                }
            }
            else
            {
                // the ciAddr MUST NOT be 0.0.0.0 for Renew and Rebind
                if (!args.RequestMessage.IsBroadcast)
                {
                    // renew is unicast
                    // NOTE: this will not happen if the v4 broadcast interface used at startup,
                    //		 but handling of DHCPv4 renew/rebind is the same anyway
                    requestState = RequestState.Renewing;
                }
                else
                {
                    // rebind is broadcast
                    requestState = RequestState.Rebinding;
                }
            }

            if ((requestState == RequestState.InitReboot) || (requestState == RequestState.Selecting))
            {
                if (args.RequestOptions.AddressRequest == null)
                {
                    Logger.WriteDebug(this, "Ignoring REQUEST " + RequestStateString.GetName(requestState) + " message: Requested IP option is null");
                    return; // if processing should not continue
                }

                if (requestState == RequestState.Selecting)
                {
                    // if the client provided a ServerID option, then it MUST
                    // match our configured ServerID, otherwise ignore the request
                    InternetAddress serverIdentifier = new InternetAddress(args.RequestOptions.ServerIdentifier);
                    //InternetAddress localServerIdentifier = new InternetAddress(((IPEndPoint)_dhcpSocket.LocalEndPoint).Address.GetAddressBytes());
                    InternetAddress localServerIdentifier = new InternetAddress(this.InterfaceAddress);
                    if (!serverIdentifier.Equals(localServerIdentifier))
                    {
                        Logger.WriteDebug(this, "Ignoring REQUEST " + RequestStateString.GetName(requestState) + " message: "
                            + "Requested ServerId: " + serverIdentifier.ToString()
                            + " Local ServerId: " + localServerIdentifier.ToString());
                        return; // if processing should not continue
                    }
                }
            }
            else
            {	// type == Renewing or Rebinding
                if (args.RequestOptions.AddressRequest != null)
                {
                    Logger.WriteDebug(this, "Ignoring REQUEST " + RequestStateString.GetName(requestState) + " message: "
                        + "Requested IP option is not null");
                    return; // if processing should not continue
                }
            }

            //  End pre-process validation
            #endregion Pre-Processing

            Logger.WriteDebug(this, "Processing REQUEST " + RequestStateString.GetName(requestState) + " message");

            //TODO:  should also check for ip on link

            if (args.RequestOptions.AddressRequest != null)
            {
                args.ResponseBinding.Address = new InternetAddress(args.RequestOptions.AddressRequest);
            }

            BindingLease assignment = _bindmgr.GetAssigned(args.ResponseBinding);
            if (assignment == null)
            {
                args.ResponseMessage.AddOption(DhcpOption.DhcpMessage, Encoding.UTF8.GetBytes("No binding available for client"));
                Logger.WriteDebug(this, "REQUEST " + RequestStateString.GetName(requestState) + " message: No binding available for client sending NAK");
                this.SendNak(args);
            }
            else
            {
                this.SendAck(args, assignment);
                this.OnLeaseAcknowledged(this, new DhcpLeaseEventArgs(assignment.Address, assignment));
            }
        }