⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 autonet.c

📁 See Hanoi.cpp for the implementation of this cla
💻 C
📖 第 1 页 / 共 2 页
字号:
                    //
                    SetDhcpConfig(pDhcp);
    
					pDhcp->IPAddr = IPAddr;
                    TakeNetDown(pDhcp, FALSE, TRUE);  // FALSE == retain IPAddr from the DHCPOFFER

                    RequestDHCPAddr(pDhcp->Name, pDhcp->Nte, pDhcp->NteContext, 
						pDhcp->PhysAddr, ETH_ADDR_LEN);

					CTEFreeLock(&pDhcp->Lock, 0);
					FreeDhcpInfo(pDhcp);

                    DEBUGMSG(ZONE_FUNCTION|ZONE_AUTOIP, (L"DHCP:-ProcessAutoIP\n"));
                    return;
                } else {
                    //
                    // No DHCP server on this net, reschedule this timer to keep checking.
                    //
                    StartAutoIPTimer(pDhcp);
                }
            } else {
                DEBUGMSG(ZONE_AUTOIP, (L"DHCP:ProcessAutoIP - DhcpInitSock failed!\n"));
            }
        } else {
            DEBUGMSG(ZONE_AUTOIP, (L"DHCP:ProcessAutoIP - SetDHCPNTE failed!\n"));
        }
        CTEFreeLock(&v_GlobalListLock, 0);
        CTEFreeLock(&pDhcp->Lock, 0);

    } else {
		CTEFreeLock(&v_GlobalListLock, 0);
        DEBUGMSG(ZONE_AUTOIP, (L"DHCP:ProcessAutoIP - FindDhcp failed!\n"));
    }
    DEBUGMSG(ZONE_FUNCTION|ZONE_AUTOIP, (L"DHCP:-ProcessAutoIP\n"));
}   // ProcessAutoIP


extern DhcpInfo	*v_pCurrent;

//
// This function is called by the IP component to indicate the status of a gratuitous ARP
// (i.e. "no response" is good. A response usually implies an IP address conflict)
//
void
ARPResult(
    IPAddr IPAddr,
    uint Result
    )
{
    DhcpInfo	*pDhcp;
#ifdef DEBUG
    TCHAR Addr[32];
#endif

    DEBUGMSG(ZONE_AUTOIP, (L"DHCP:+ARPResult\n"));

    CTEGetLock(&v_GlobalListLock, 0);
    if (pDhcp = v_pCurrent) {
        if (pDhcp->IPAddr == IPAddr) {
            pDhcp->ARPResult = Result;
            if (pDhcp->ARPEvent) {
                DEBUGMSG(ZONE_AUTOIP, (L"DHCP:ARPResult - setting event\n"));
                SetEvent(pDhcp->ARPEvent);
            }
        } else {
            DEBUGMSG(ZONE_AUTOIP, (L"DHCP:ARPResult - IPAddress %s != Current IPAddress\n", AddrToString(IPAddr, Addr)));
        }
    } else {
        DEBUGMSG(ZONE_AUTOIP, (L"DHCP:ARPResult - v_pCurrent == NULL\n"));
    }
    CTEFreeLock(&v_GlobalListLock, 0);
    
    DEBUGMSG(ZONE_AUTOIP, (L"DHCP:-ARPResult\n"));
}   // AutoIP_ARPResult


#define GRAND_HASHING_RETRIES 5 

//================================================================================
//  GrandHashing does all the work.  It updates seed and returns an ip address
//  is in the specified subnet (with required mask) based on the random # and the
//  hardware address.
//================================================================================
uint                            //  Ip address o/p after hashing
GrandHashing(
    IN      uchar * HwAddress,  //  Hardware addres of the card
    IN      uint    HwLen,      //  Hardware length
    IN OUT  uint *  Seed,       //  In: orig value, Out: final value
    IN      uint    Mask,       //  Subnet mask to generate ip addr in
    IN      uint    Subnet      //  Subnet address to generate ip addr in
    )
{
    DWORD   Hash, Shift;
    uint    Result;
    int     cRetries;
    uchar * Addr;
    uint    Len;

    if (*Seed == 0) {
        *Seed = (uint)CeGetRandomSeed();
    }

    for (cRetries = GRAND_HASHING_RETRIES; cRetries; cRetries--) {
        Addr = HwAddress;
        Len = HwLen;
        *Seed = (*Seed)*1103515245 + 12345 ;//  Random # generator as in K&R
        Hash = (*Seed) >> 16 ;
        Hash <<= 16;
        *Seed = (*Seed)*1103515245 + 12345 ;//  Random # generator as in K&R
        Hash += (*Seed) >> 16;
    
        // Now Hash contains the 32 bit Random # we need.
        Shift = Hash % sizeof(uint) ;      //  Decide the # of bytes to shift hw-address
    
        while( Len -- ) {
            Hash += (*Addr++) << (8 * Shift);
            Shift = (Shift + 1 )% sizeof(uint);
        }

        Result = Hash & ~Mask;

        // Check for bcast addresses
        if (Result && (Result != ~Mask)) {
            return Result | Subnet;       //  Now restrict hash to be in required subnet
        }
    }

    // In the highly unlikely case that 5 consecutive hashes yielded bcast addresses,
    // return a non-bcast address
    return (GRAND_HASHING_RETRIES & ~Mask) | Subnet;
}


//
// This function is called when the DHCP client has not received any response from a DHCP server
//
STATUS
AutoIP(
    DhcpInfo *pDhcp
    )
{
    uint i;
    uint Result;
    uint Seed;
    uint HwLen;
    uint AttemptedAddress;
    uint Mask;
    uint Subnet;
    uchar * HwAddress;
    uint SaveIPAddr;
    uint AutoInterval;
#ifdef DEBUG
    TCHAR Addr[32];
#endif

    DEBUGMSG(ZONE_FUNCTION|ZONE_AUTOIP, (L"DHCP:+AutoIP\n"));

    pDhcp->SFlags &= ~DHCPSTATE_AUTO_CFG_IP;    // IPAddr not autoconfigured.

    // If there is no DHCP server out there and we have a valid IPAddr, ping the default
    // gateway to make sure we are still on the same subnet.
    if (CouldPingGateway(pDhcp)) {
        DEBUGMSG(ZONE_FUNCTION|ZONE_AUTOIP, (L"DHCP:-AutoIP - Still on DHCP server subnet\n"));
        return DHCP_SUCCESS;
    }

    Mask      = pDhcp->AutoMask;
    Subnet    = pDhcp->AutoSubnet;
    HwAddress = pDhcp->PhysAddr;
    HwLen     = sizeof(pDhcp->PhysAddr);
    Seed      = pDhcp->AutoSeed;
    SaveIPAddr = pDhcp->IPAddr;
    Result = ERROR_GEN_FAILURE;

    //
    // Tell tcpstk we are doing DHCP + AutoCfg
    //
    if (!(*pfnSetDHCPNTE)(pDhcp->NteContext, NULL, NULL, &Seed)) {
        DEBUGMSG(ZONE_AUTOIP, (L"DHCP:AutoIP - SetDHCPNTE failed!\n"));
        goto ai_exit;
    }

    if (pDhcp->AutoIPAddr) {
        //
        // Use our previously autoconfigured IP address
        //
        AttemptedAddress = pDhcp->AutoIPAddr;
    } else {
        AttemptedAddress = GrandHashing( HwAddress, HwLen, &Seed, Mask, Subnet );
    }

    i = DHCP_IPAUTOCONFIGURATION_ATTEMPTS;

    do {
        if (pDhcp->SFlags & DHCPSTATE_SAW_DHCP_SRV) {
            //
            // If we ever see a DHCP server on our net, then abort IP autoconfiguration immediately
            //
            DEBUGMSG(ZONE_AUTOIP, (L"DHCP:AutoIP:DHCP server on net. Aborting autoconfig\n"));
            goto ai_exit;
        }

        DEBUGMSG(ZONE_AUTOIP, (L"DHCP:AutoIP:Trying autoconfig address: %s\n", AddrToString(AttemptedAddress, Addr)));

        if ((AttemptedAddress & DHCP_RESERVED_AUTOCFG_MASK) == DHCP_RESERVED_AUTOCFG_SUBNET) {
            // address is in reserved range, dont use it..
            goto ai_next;
        } 

        pDhcp->ARPResult = ERROR_SUCCESS;
        pDhcp->IPAddr = AttemptedAddress;
        ResetEvent(pDhcp->ARPEvent);

        //
        // Among other things, setting the NTE addr causes ARP to probe for existence of this IP addr.
        // Just wait a few seconds to see if it is a dup.
        //
        if ((*pfnIPSetNTEAddr)((ushort)pDhcp->NteContext, NULL, pDhcp->IPAddr, Mask, 0)) {
            WaitForSingleObject(pDhcp->ARPEvent, ARP_RESPONSE_WAIT);
            if (ERROR_SUCCESS == pDhcp->ARPResult) {
                AutoInterval = pDhcp->AutoInterval; // Remember interval
                pDhcp->AutoInterval = 2;            // Send an additional DHCP discover right away.
                pDhcp->AutoIPAddr   = AttemptedAddress;
                pDhcp->AutoSeed     = Seed;    
                pDhcp->SubnetMask   = Mask;
                pDhcp->SFlags |= DHCPSTATE_AUTO_CFG_IP;     // IPAddr is autoconfigured.
                StartAutoIPTimer(pDhcp);
                pDhcp->AutoInterval = AutoInterval; // Restore interval
                CallAfd(AddInterface)(pDhcp->Name, pDhcp->Nte, 
                	pDhcp->NteContext, 0, pDhcp->IPAddr, 
                    pDhcp->SubnetMask, 0, pDhcp->DNS, 0, pDhcp->WinsServer); 
                NotifyXxxChange(g_hAddrChangeEvent);
                Result = DHCP_SUCCESS;
                break;
            } else {
                //
                // Tell IP to stop using the address and mark this NTE for another try
                //
                (*pfnIPSetNTEAddr)((ushort)pDhcp->NteContext, NULL, 0, 0, 0);
                (*pfnSetDHCPNTE)(pDhcp->NteContext, NULL, NULL, &Seed);
            }
        } else {
            DEBUGMSG(ZONE_AUTOIP, (L"DHCP:AutoIP - IPSetNTEAddr failed!\n"));
            goto ai_exit;
        }
        
ai_next:
        AttemptedAddress = GrandHashing( HwAddress, HwLen, &Seed, Mask, Subnet );
        i --;

    } while (i);

    if (0 == i) {                      //  Tried everything and still could not match
        (*pfnIPSetNTEAddr)((ushort)pDhcp->NteContext, NULL, 0, 0, 0);
        DEBUGMSG(ZONE_AUTOIP, (L"DHCP:AutoIP - Gave up autoconfiguration\n"));
    }

ai_exit:
    if (Result) {
        pDhcp->IPAddr = SaveIPAddr;
    }
    ClearDHCPNTE(pDhcp);
    DEBUGMSG(ZONE_FUNCTION|ZONE_AUTOIP, (L"DHCP:-AutoIP %d\n", Result));
    return Result;
}   // AutoIP



⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -