netutils/dhcpd: handshake the dhcpd message with server port.
resolve the dhcpd compatibility issues on some strict system, such as Windows XP,7,10 Signed-off-by: chao.an <anchao@xiaomi.com>
This commit is contained in:
parent
017f5ed65c
commit
4c256e7db3
@ -882,45 +882,6 @@ static inline int dhcpd_socket(void)
|
|||||||
return sockfd;
|
return sockfd;
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
|
||||||
* Name: dhcpd_openresponder
|
|
||||||
****************************************************************************/
|
|
||||||
|
|
||||||
static inline int dhcpd_openresponder(void)
|
|
||||||
{
|
|
||||||
struct sockaddr_in addr;
|
|
||||||
int sockfd;
|
|
||||||
int ret;
|
|
||||||
|
|
||||||
ninfo("Responder: %08" PRIx32 "\n", ntohl(g_state.ds_serverip));
|
|
||||||
|
|
||||||
/* Create a socket to listen for requests from DHCP clients */
|
|
||||||
|
|
||||||
sockfd = dhcpd_socket();
|
|
||||||
if (sockfd < 0)
|
|
||||||
{
|
|
||||||
nerr("ERROR: socket failed: %d\n", errno);
|
|
||||||
return ERROR;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Bind the socket to a local port. */
|
|
||||||
|
|
||||||
addr.sin_family = AF_INET;
|
|
||||||
addr.sin_port = 0;
|
|
||||||
addr.sin_addr.s_addr = g_state.ds_serverip;
|
|
||||||
|
|
||||||
ret = bind(sockfd, (struct sockaddr *)&addr, sizeof(struct sockaddr_in));
|
|
||||||
if (ret < 0)
|
|
||||||
{
|
|
||||||
nerr("ERROR: bind failed, port=%d addr=%08lx: %d\n",
|
|
||||||
addr.sin_port, (long)addr.sin_addr.s_addr, errno);
|
|
||||||
close(sockfd);
|
|
||||||
return ERROR;
|
|
||||||
}
|
|
||||||
|
|
||||||
return sockfd;
|
|
||||||
}
|
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
* Name: dhcpd_initpacket
|
* Name: dhcpd_initpacket
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
@ -958,13 +919,11 @@ static void dhcpd_initpacket(uint8_t mtype)
|
|||||||
* Name: dhcpd_sendpacket
|
* Name: dhcpd_sendpacket
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
static int dhcpd_sendpacket(int bbroadcast)
|
static int dhcpd_sendpacket(int sockfd, int bbroadcast)
|
||||||
{
|
{
|
||||||
struct sockaddr_in addr;
|
struct sockaddr_in addr;
|
||||||
in_addr_t ipaddr;
|
in_addr_t ipaddr;
|
||||||
int sockfd;
|
|
||||||
int len;
|
int len;
|
||||||
int ret = ERROR;
|
|
||||||
|
|
||||||
#ifdef CONFIG_NETUTILS_DHCPD_IGNOREBROADCAST
|
#ifdef CONFIG_NETUTILS_DHCPD_IGNOREBROADCAST
|
||||||
/* This is a hack. I've had problems with Windows machines responding
|
/* This is a hack. I've had problems with Windows machines responding
|
||||||
@ -1025,9 +984,6 @@ static int dhcpd_sendpacket(int bbroadcast)
|
|||||||
* cannot re-use the listener socket because it is not bound correctly
|
* cannot re-use the listener socket because it is not bound correctly
|
||||||
*/
|
*/
|
||||||
|
|
||||||
sockfd = dhcpd_openresponder();
|
|
||||||
if (sockfd >= 0)
|
|
||||||
{
|
|
||||||
/* Then send the response to the DHCP client port at that address */
|
/* Then send the response to the DHCP client port at that address */
|
||||||
|
|
||||||
memset(&addr, 0, sizeof(struct sockaddr_in));
|
memset(&addr, 0, sizeof(struct sockaddr_in));
|
||||||
@ -1041,19 +997,16 @@ static int dhcpd_sendpacket(int bbroadcast)
|
|||||||
ninfo("sendto %08lx:%04x len=%d\n",
|
ninfo("sendto %08lx:%04x len=%d\n",
|
||||||
(long)ntohl(addr.sin_addr.s_addr), ntohs(addr.sin_port), len);
|
(long)ntohl(addr.sin_addr.s_addr), ntohs(addr.sin_port), len);
|
||||||
|
|
||||||
ret = sendto(sockfd, &g_state.ds_outpacket, len, 0,
|
return sendto(sockfd, &g_state.ds_outpacket, len, 0,
|
||||||
(struct sockaddr *)&addr, sizeof(struct sockaddr_in));
|
(struct sockaddr *)&addr, sizeof(struct sockaddr_in));
|
||||||
close(sockfd);
|
|
||||||
}
|
|
||||||
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
* Name: dhcpd_sendoffer
|
* Name: dhcpd_sendoffer
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
static inline int dhcpd_sendoffer(in_addr_t ipaddr, uint32_t leasetime)
|
static inline int dhcpd_sendoffer(int sockfd, in_addr_t ipaddr,
|
||||||
|
uint32_t leasetime)
|
||||||
{
|
{
|
||||||
in_addr_t netaddr;
|
in_addr_t netaddr;
|
||||||
#ifdef HAVE_DNSIP
|
#ifdef HAVE_DNSIP
|
||||||
@ -1091,9 +1044,9 @@ static inline int dhcpd_sendoffer(in_addr_t ipaddr, uint32_t leasetime)
|
|||||||
/* Send the offer response */
|
/* Send the offer response */
|
||||||
|
|
||||||
#ifdef CONFIG_NETUTILS_DHCPD_IGNOREBROADCAST
|
#ifdef CONFIG_NETUTILS_DHCPD_IGNOREBROADCAST
|
||||||
return dhcpd_sendpacket(true);
|
return dhcpd_sendpacket(sockfd, true);
|
||||||
#else
|
#else
|
||||||
return dhcpd_sendpacket(false);
|
return dhcpd_sendpacket(sockfd, false);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1101,20 +1054,20 @@ static inline int dhcpd_sendoffer(in_addr_t ipaddr, uint32_t leasetime)
|
|||||||
* Name: dhcpd_sendnak
|
* Name: dhcpd_sendnak
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
static int dhcpd_sendnak(void)
|
static int dhcpd_sendnak(int sockfd)
|
||||||
{
|
{
|
||||||
/* Initialize and send the NAK response */
|
/* Initialize and send the NAK response */
|
||||||
|
|
||||||
dhcpd_initpacket(DHCPNAK);
|
dhcpd_initpacket(DHCPNAK);
|
||||||
memcpy(g_state.ds_outpacket.ciaddr, g_state.ds_inpacket.ciaddr, 4);
|
memcpy(g_state.ds_outpacket.ciaddr, g_state.ds_inpacket.ciaddr, 4);
|
||||||
return dhcpd_sendpacket(true);
|
return dhcpd_sendpacket(sockfd, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
* Name: dhcpd_sendack
|
* Name: dhcpd_sendack
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
int dhcpd_sendack(in_addr_t ipaddr)
|
int dhcpd_sendack(int sockfd, in_addr_t ipaddr)
|
||||||
{
|
{
|
||||||
uint32_t leasetime = CONFIG_NETUTILS_DHCPD_LEASETIME;
|
uint32_t leasetime = CONFIG_NETUTILS_DHCPD_LEASETIME;
|
||||||
in_addr_t netaddr;
|
in_addr_t netaddr;
|
||||||
@ -1153,9 +1106,9 @@ int dhcpd_sendack(in_addr_t ipaddr)
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef CONFIG_NETUTILS_DHCPD_IGNOREBROADCAST
|
#ifdef CONFIG_NETUTILS_DHCPD_IGNOREBROADCAST
|
||||||
if (dhcpd_sendpacket(true) < 0)
|
if (dhcpd_sendpacket(sockfd, true) < 0)
|
||||||
#else
|
#else
|
||||||
if (dhcpd_sendpacket(false) < 0)
|
if (dhcpd_sendpacket(sockfd, false) < 0)
|
||||||
#endif
|
#endif
|
||||||
{
|
{
|
||||||
return ERROR;
|
return ERROR;
|
||||||
@ -1169,7 +1122,7 @@ int dhcpd_sendack(in_addr_t ipaddr)
|
|||||||
* Name: dhcpd_discover
|
* Name: dhcpd_discover
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
static inline int dhcpd_discover(void)
|
static inline int dhcpd_discover(int sockfd)
|
||||||
{
|
{
|
||||||
struct lease_s *lease;
|
struct lease_s *lease;
|
||||||
in_addr_t ipaddr;
|
in_addr_t ipaddr;
|
||||||
@ -1241,14 +1194,14 @@ static inline int dhcpd_discover(void)
|
|||||||
|
|
||||||
/* Send the offer response */
|
/* Send the offer response */
|
||||||
|
|
||||||
return dhcpd_sendoffer(ipaddr, leasetime);
|
return dhcpd_sendoffer(sockfd, ipaddr, leasetime);
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
* Name: dhcpd_request
|
* Name: dhcpd_request
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
static inline int dhcpd_request(void)
|
static inline int dhcpd_request(int sockfd)
|
||||||
{
|
{
|
||||||
struct lease_s *lease;
|
struct lease_s *lease;
|
||||||
in_addr_t ipaddr = 0;
|
in_addr_t ipaddr = 0;
|
||||||
@ -1388,12 +1341,12 @@ static inline int dhcpd_request(void)
|
|||||||
if (response == DHCPACK)
|
if (response == DHCPACK)
|
||||||
{
|
{
|
||||||
ninfo("ACK IP %08lx\n", (long)ipaddr);
|
ninfo("ACK IP %08lx\n", (long)ipaddr);
|
||||||
dhcpd_sendack(ipaddr);
|
dhcpd_sendack(sockfd, ipaddr);
|
||||||
}
|
}
|
||||||
else if (response == DHCPNAK)
|
else if (response == DHCPNAK)
|
||||||
{
|
{
|
||||||
ninfo("NAK IP %08lx\n", (long)ipaddr);
|
ninfo("NAK IP %08lx\n", (long)ipaddr);
|
||||||
dhcpd_sendnak();
|
dhcpd_sendnak(sockfd);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -1604,12 +1557,12 @@ int dhcpd_run(FAR const char *interface)
|
|||||||
{
|
{
|
||||||
case DHCPDISCOVER:
|
case DHCPDISCOVER:
|
||||||
ninfo("DHCPDISCOVER\n");
|
ninfo("DHCPDISCOVER\n");
|
||||||
dhcpd_discover();
|
dhcpd_discover(sockfd);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case DHCPREQUEST:
|
case DHCPREQUEST:
|
||||||
ninfo("DHCPREQUEST\n");
|
ninfo("DHCPREQUEST\n");
|
||||||
dhcpd_request();
|
dhcpd_request(sockfd);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case DHCPDECLINE:
|
case DHCPDECLINE:
|
||||||
|
Loading…
x
Reference in New Issue
Block a user