?? dhcp_support.c
字號:
/*==========================================================================//// dhcp_support.c//// Support code == friendly API for DHCP client////==========================================================================//####ECOSPDCOPYRIGHTBEGIN####//// Copyright (C) 2000, 2001, 2002 Red Hat, Inc.// All Rights Reserved.//// Permission is granted to use, copy, modify and redistribute this// file.////####ECOSPDCOPYRIGHTEND####//==========================================================================//#####DESCRIPTIONBEGIN####//// Author(s): hmt// Contributors: gthomas// Date: 2000-07-01// Purpose: DHCP support// Description: ////####DESCRIPTIONEND####////========================================================================*/#include <pkgconf/system.h>#include <pkgconf/net.h>/* Define these locally because we are porting this code from a later package, * therefore these are not defined in pkgconf/net.h */#define DHCP_MIB_VERSION 9#define CYGPKG_NET_DHCP#define CYGOPT_NET_DHCP_DHCP_THREAD#ifdef CYGPKG_NET_DHCP#include <network.h>#include <dhcp.h>#if defined(GATEWAY) && defined(DHCPS)#if PROD_NAME == 0#include "timer.h"Timer LinkStatusTimer;#endif /* Inform DHCP Server application */extern void dhcpsSetDNS ( unsigned long prim_dns_addr, unsigned long sec_dns_addr);#endif//#define CYGDBG_NET_DHCP_CHATTER#if defined(GATEWAY) /* Inform Fast Routing module */extern void FR_Main_WanIP_update();#endiftypedef struct MIB_DHCP_s{ unsigned long IPAddr; unsigned long SubnetMask; unsigned long GwyAddr; unsigned long PrimaryDNS; unsigned long SecondaryDNS;}MIB_DHCP;#if defined(GATEWAY)typedef struct MIB_IP_LAN_s{ unsigned long IPAddr; unsigned long SubnetMask;}MIB_IP_LAN;extern MIB_IP_LAN mib_IP_LAN;extern in_addr_t inet_addr (char *cp);#define _string(s) #s#define string(s) _string(s)#endif#ifdef AP5XMIB_DHCP mib_DHCP= {0x34020202, 0xFFFFFF00, 0, 0, 0};#define MIB_DHCP_P (&mib_DHCP)#define SUBNETMASK (mib_DHCP.SubnetMask)#define IPADDR (mib_DHCP.IPAddr)#define GWYADDR (mib_DHCP.GwyAddr)#define PRIMARYDNS (mib_DHCP.PrimaryDNS)#define SECONDARYDNS (mib_DHCP.SecondaryDNS)#elseextern MIB_DHCP *mib_DHCP_p;#define MIB_DHCP_P (mib_DHCP_p)#define SUBNETMASK (mib_DHCP_p->SubnetMask)#define IPADDR (mib_DHCP_p->IPAddr)#define GWYADDR (mib_DHCP_p->GwyAddr)#endifextern unsigned char mib_dhcpenable;extern int SetUserConfig(void);extern void Reset(void);// ---------------------------------------------------------------------------#ifdef CYGHWR_NET_DRIVER_ETH0cyg_uint8 eth0_dhcpstate = 0;#endif#ifdef CYGHWR_NET_DRIVER_ETH1cyg_uint8 eth1_dhcpstate = 0;#endifcyg_sem_t dhcp_needs_attention;#ifdef CYGHWR_NET_DRIVER_ETH0struct dhcp_lease eth0_lease = { &dhcp_needs_attention, 0, 0, 0, 0, 0, 0 };#endif#ifdef CYGHWR_NET_DRIVER_ETH1struct dhcp_lease eth1_lease = { &dhcp_needs_attention, 0, 0, 0, 0, 0, 0 };#endif#if PROD_NAME == 0unsigned int LinkStatusCheckTimeOut(unsigned char *data){ extern int gWanPort; #define LINK_NO_CHANGE 0 #define LINK_TO_UP 1 #define LINK_TO_DOWN 2 #define TRUE 1 #define FALSE 0 static unsigned char wanPortStatusChange = LINK_NO_CHANGE; static unsigned char wanLinkUp = FALSE; if(wanPortStatusChange != LINK_NO_CHANGE) { if(wanPortStatusChange == LINK_TO_UP) initiate_dhcp(1); wanPortStatusChange = LINK_NO_CHANGE; } else { if(isPortLinkUp(gWanPort)) { if(wanLinkUp == FALSE) wanPortStatusChange = LINK_TO_UP; wanLinkUp = TRUE; } else { if(wanLinkUp == TRUE) wanPortStatusChange = LINK_TO_DOWN; wanLinkUp = FALSE; } } return 0;}#endifstatic unsigned char *add_tag(unsigned char *vp, unsigned char tag, void *val, int len){ int i; unsigned char *xp = (unsigned char *)val; *vp++ = tag; *vp++ = len; for (i = 0; i < len; i++) { *vp++ = *xp++; } return vp;}unsigned long inet_address(unsigned long addr){ return htonl(addr);}static voidbuild_bootp_record(struct bootp *bp, const char *addrs_ip, const char *addrs_netmask, const char *addrs_broadcast, const char *addrs_gateway, const char *addrs_server){ int i; in_addr_t addr; unsigned char *vp; unsigned char cookie[] = VM_RFC1048; bzero(bp, sizeof(struct bootp)); bp->bp_op = BOOTREPLY; bp->bp_htype = HTYPE_ETHERNET; bp->bp_hlen = 6; for (i = 0; i < bp->bp_hlen; i++) { bp->bp_chaddr[i] = 0xFF; } bp->bp_ciaddr.s_addr = inet_addr(addrs_ip); bp->bp_yiaddr.s_addr = inet_addr(addrs_ip); bp->bp_siaddr.s_addr = inet_addr(addrs_server); bp->bp_giaddr.s_addr = inet_addr(addrs_gateway); vp = &bp->bp_vend[0]; bcopy(&cookie, vp, sizeof(cookie)); vp += sizeof(cookie); addr = inet_addr(addrs_netmask); vp = add_tag(vp, TAG_SUBNET_MASK, &addr, sizeof(in_addr_t)); addr = inet_addr(addrs_broadcast); vp = add_tag(vp, TAG_IP_BROADCAST, &addr, sizeof(in_addr_t)); *vp = TAG_END;}/* used at init to BUILD FROM from mib or when moving from dhcp to static*/void dhcp_build_bootp(struct bootp *bp, cyg_uint32 my_addr, cyg_uint32 my_mask, cyg_uint32 gateway, cyg_uint32 server){ unsigned int i; unsigned char *vp; unsigned char cookie[] = VM_RFC1048; bzero(bp, sizeof(struct bootp)); bp->bp_op = BOOTREPLY; bp->bp_htype = HTYPE_ETHERNET; bp->bp_hlen = 6; for (i = 0; i < bp->bp_hlen; i++) { bp->bp_chaddr[i] = 0xFF; } bp->bp_ciaddr.s_addr = htonl(my_addr); bp->bp_yiaddr.s_addr = htonl(my_addr); bp->bp_siaddr.s_addr = htonl(my_addr); bp->bp_giaddr.s_addr = htonl(my_addr); vp = &bp->bp_vend[0]; bcopy(&cookie, vp, sizeof(cookie)); vp += sizeof(cookie); my_mask = htonl(my_mask); vp = add_tag(vp, TAG_SUBNET_MASK, &my_mask, sizeof(in_addr_t)); if(gateway){/* add default gateway tag */ gateway = htonl(gateway); vp = add_tag(vp, TAG_GATEWAY, &gateway, sizeof(in_addr_t)); } *vp = TAG_END;}#define INIT_WAN_ONLY 1#define INIT_LAN_ONLY 2#define INIT_ALL 0voidinit_my_network_interfaces(int flag){ extern unsigned char mib_version;#ifdef CYGHWR_NET_DRIVER_ETH0#ifdef CYGHWR_NET_DRIVER_ETH0_BOOTP// Perform a complete initialization, using BOOTP/DHCP eth0_up = true; if (do_bootp(eth0_name, ð0_bootp_data)) {#ifdef CYGHWR_NET_DRIVER_ETH0_BOOTP_SHOW show_bootp(eth0_name, ð0_bootp_data);#endif } else { //diag_printf("BOOTP failed on eth0\n"); eth0_up = false; }#elif defined(CYGHWR_NET_DRIVER_ETH0_ADDRS_IP) eth0_up = true; if(flag != INIT_LAN_ONLY) { if(mib_version != DHCP_MIB_VERSION ) build_bootp_record(ð0_bootp_data, string(CYGHWR_NET_DRIVER_ETH0_ADDRS_IP), string(CYGHWR_NET_DRIVER_ETH0_ADDRS_NETMASK), string(CYGHWR_NET_DRIVER_ETH0_ADDRS_BROADCAST), 0/*string(CYGHWR_NET_DRIVER_ETH0_ADDRS_IP)*/, 0/*string(CYGHWR_NET_DRIVER_ETH0_ADDRS_IP)*/); else dhcp_build_bootp(ð0_bootp_data, IPADDR, SUBNETMASK, GWYADDR, 0); show_bootp(eth0_name, ð0_bootp_data); }#endif#endif#ifdef CYGHWR_NET_DRIVER_ETH1#ifdef CYGHWR_NET_DRIVER_ETH1_BOOTP// Perform a complete initialization, using BOOTP/DHCP eth1_up = true; if (do_bootp(eth1_name, ð1_bootp_data)) {#ifdef CYGHWR_NET_DRIVER_ETH1_BOOTP_SHOW show_bootp(eth1_name, ð1_bootp_data);#endif } else { //diag_printf("BOOTP failed on eth1\n"); eth1_up = false; }#elif defined(CYGHWR_NET_DRIVER_ETH1_ADDRS_IP) eth1_up = true; if(flag != INIT_WAN_ONLY) { if(mib_version != DHCP_MIB_VERSION ) { build_bootp_record(ð1_bootp_data, string(CYGHWR_NET_DRIVER_ETH1_ADDRS_IP), string(CYGHWR_NET_DRIVER_ETH1_ADDRS_NETMASK), string(CYGHWR_NET_DRIVER_ETH1_ADDRS_BROADCAST), 0/*string(CYGHWR_NET_DRIVER_ETH1_ADDRS_GATEWAY)*/, 0/*string(CYGHWR_NET_DRIVER_ETH1_ADDRS_SERVER)*/); mib_IP_LAN.IPAddr = inet_addr(string(CYGHWR_NET_DRIVER_ETH1_ADDRS_IP)); mib_IP_LAN.IPAddr = htonl(mib_IP_LAN.IPAddr); mib_IP_LAN.SubnetMask = inet_addr(string(CYGHWR_NET_DRIVER_ETH1_ADDRS_NETMASK)); mib_IP_LAN.SubnetMask = htonl(mib_IP_LAN.SubnetMask); } else { if(mib_IP_LAN.IPAddr == 0) { mib_IP_LAN.IPAddr = inet_addr(string(CYGHWR_NET_DRIVER_ETH1_ADDRS_IP)); mib_IP_LAN.IPAddr = htonl(mib_IP_LAN.IPAddr); } if(mib_IP_LAN.SubnetMask == 0) { mib_IP_LAN.SubnetMask = inet_addr(string(CYGHWR_NET_DRIVER_ETH1_ADDRS_NETMASK)); mib_IP_LAN.SubnetMask = htonl(mib_IP_LAN.SubnetMask); } dhcp_build_bootp(ð1_bootp_data, mib_IP_LAN.IPAddr, mib_IP_LAN.SubnetMask, 0, 0); } show_bootp(eth1_name, ð1_bootp_data); }#endif#endif#ifdef CYGHWR_NET_DRIVER_ETH0#ifndef CYGHWR_NET_DRIVER_ETH0_MANUAL if (eth0_up) { if (!init_net(eth0_name, ð0_bootp_data)) { //diag_printf("Network initialization failed for eth0\n"); eth0_up = false; } }#endif#endif#ifdef CYGHWR_NET_DRIVER_ETH1#ifndef CYGHWR_NET_DRIVER_ETH1_MANUAL if (eth1_up) { if (!init_net(eth1_name, ð1_bootp_data)) { //diag_printf("Network initialization failed for eth1\n"); eth1_up = false; } }#endif#endif}#define DHCP_FIX 1void update_IP_Info(void){ struct bootp *bp; unsigned char *op, *ap = 0; struct in_addr addr[32]; unsigned char name[128]; int i, len; unsigned long tmpaddr;#ifdef DHCP_FIX unsigned long dnsServer = 0, defaultGW =0 ;#endif#ifdef CYGDBG_NET_DHCP_CHATTER diag_printf("update_IP_Info\n");#endif bp = ð0_bootp_data; IPADDR = inet_address(eth0_bootp_data.bp_yiaddr.s_addr); GWYADDR = inet_address(eth0_bootp_data.bp_giaddr.s_addr);#ifdef CYGDBG_NET_DHCP_CHATTER diag_printf("update_IP_Info: set ip %x\n", mib_DHCP_p->IPAddr);#endif if (bp->bp_vend[0]) { op = &bp->bp_vend[4]; while (*op != TAG_END) { switch (*op) { case TAG_SUBNET_MASK: ap = (unsigned char *) & tmpaddr; len = *(op + 1); for (i = 0; i < len; i++) { *ap++ = *(op + i + 2); } while (len > 0) { len -= sizeof(struct in_addr); ap += sizeof(struct in_addr); } SUBNETMASK = inet_address(tmpaddr); break; case TAG_GATEWAY:#ifdef DHCP_FIX defaultGW = 1;#endif ap = (unsigned char *) & tmpaddr; len = *(op + 1); for (i = 0; i < len; i++) { *ap++ = *(op + i + 2); } while (len > 0) { len -= sizeof(struct in_addr); ap += sizeof(struct in_addr); } GWYADDR = inet_address(tmpaddr); break; case TAG_IP_BROADCAST: ap = (unsigned char *) & addr[0]; len = *(op + 1); for (i = 0; i < len; i++) { *ap++ = *(op + i + 2); } if (*op == TAG_SUBNET_MASK)
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -