Beispiel #1
0
DWORD DSLeaseIpAddress( PipeSendFunc Send, COMM_DHCP_REQ *Req ) {
    COMM_DHCP_REPLY Reply;
    PDHCP_ADAPTER Adapter;
    struct protocol* proto;

    ApiLock();

    Adapter = AdapterFindIndex( Req->AdapterIndex );

    Reply.Reply = Adapter ? 1 : 0;

    if( Adapter ) {
        proto = find_protocol_by_adapter( &Adapter->DhclientInfo );
        if (proto)
            remove_protocol(proto);

        add_protocol( Adapter->DhclientInfo.name,
                      Adapter->DhclientInfo.rfdesc, got_one,
                      &Adapter->DhclientInfo );

        Adapter->DhclientInfo.client->state = S_INIT;
        state_reboot(&Adapter->DhclientInfo);

        if (AdapterStateChangedEvent != NULL)
            SetEvent(AdapterStateChangedEvent);
    }

    ApiUnlock();

    return Send( &Reply );
}
Beispiel #2
0
DWORD DSStaticRefreshParams( PipeSendFunc Send, COMM_DHCP_REQ *Req ) {
    NTSTATUS Status;
    COMM_DHCP_REPLY Reply;
    PDHCP_ADAPTER Adapter;
    struct protocol* proto;

    ApiLock();

    Adapter = AdapterFindIndex( Req->AdapterIndex );

    Reply.Reply = Adapter ? 1 : 0;

    if( Adapter ) {
        if (Adapter->NteContext)
        {
            DeleteIPAddress( Adapter->NteContext );
            Adapter->NteContext = 0;
        }
        if (Adapter->RouterMib.dwForwardNextHop)
        {
            DeleteIpForwardEntry( &Adapter->RouterMib );
            Adapter->RouterMib.dwForwardNextHop = 0;
        }
        
        Adapter->DhclientState.state = S_STATIC;
        proto = find_protocol_by_adapter( &Adapter->DhclientInfo );
        if (proto)
            remove_protocol(proto);
        Status = AddIPAddress( Req->Body.StaticRefreshParams.IPAddress,
                               Req->Body.StaticRefreshParams.Netmask,
                               Req->AdapterIndex,
                               &Adapter->NteContext,
                               &Adapter->NteInstance );
        Reply.Reply = NT_SUCCESS(Status);

        if (AdapterStateChangedEvent != NULL)
            SetEvent(AdapterStateChangedEvent);
    }

    ApiUnlock();

    return Send( &Reply );
}
Beispiel #3
0
DWORD DSReleaseIpAddressLease( PipeSendFunc Send, COMM_DHCP_REQ *Req ) {
    COMM_DHCP_REPLY Reply;
    PDHCP_ADAPTER Adapter;
    struct protocol* proto;

    ApiLock();

    Adapter = AdapterFindIndex( Req->AdapterIndex );

    Reply.Reply = Adapter ? 1 : 0;

    if( Adapter ) {
        if (Adapter->NteContext)
        {
            DeleteIPAddress( Adapter->NteContext );
            Adapter->NteContext = 0;
        }
        if (Adapter->RouterMib.dwForwardNextHop)
        {
            DeleteIpForwardEntry( &Adapter->RouterMib );
            Adapter->RouterMib.dwForwardNextHop = 0;
        }

        proto = find_protocol_by_adapter( &Adapter->DhclientInfo );
        if (proto)
           remove_protocol(proto);

        Adapter->DhclientInfo.client->active = NULL;
        Adapter->DhclientInfo.client->state = S_INIT;

        if (AdapterStateChangedEvent != NULL)
            SetEvent(AdapterStateChangedEvent);
    }

    ApiUnlock();

    return Send( &Reply );
}
Beispiel #4
0
/*
 * XXX Figure out the way to bind a specific adapter to a socket.
 */
DWORD WINAPI AdapterDiscoveryThread(LPVOID Context) {
    PMIB_IFTABLE Table = (PMIB_IFTABLE) malloc(sizeof(MIB_IFTABLE));
    DWORD Error, Size = sizeof(MIB_IFTABLE);
    PDHCP_ADAPTER Adapter = NULL;
    HANDLE AdapterStateChangedEvent = (HANDLE)Context;
    struct interface_info *ifi = NULL;
    struct protocol *proto;
    int i, AdapterCount = 0, Broadcast;

    /* FIXME: Kill this thread when the service is stopped */

    do {
       DH_DbgPrint(MID_TRACE,("Getting Adapter List...\n"));

       while( (Error = GetIfTable(Table, &Size, 0 )) ==
               ERROR_INSUFFICIENT_BUFFER ) {
           DH_DbgPrint(MID_TRACE,("Error %d, New Buffer Size: %d\n", Error, Size));
           free( Table );
           Table = (PMIB_IFTABLE) malloc( Size );
       }

       if( Error != NO_ERROR )
       {
           /* HACK: We are waiting until TCP/IP starts */
           Sleep(2000);
           continue;
       }

       DH_DbgPrint(MID_TRACE,("Got Adapter List (%d entries)\n", Table->dwNumEntries));

       for( i = Table->dwNumEntries - 1; i >= 0; i-- ) {
            DH_DbgPrint(MID_TRACE,("Getting adapter %d attributes\n",
                                   Table->table[i].dwIndex));

            ApiLock();

            if ((Adapter = AdapterFindByHardwareAddress(Table->table[i].bPhysAddr, Table->table[i].dwPhysAddrLen)))
            {
                proto = find_protocol_by_adapter(&Adapter->DhclientInfo);

                /* This is an existing adapter */
                if (InterfaceConnected(&Table->table[i])) {
                    /* We're still active so we stay in the list */
                    ifi = &Adapter->DhclientInfo;

                    /* This is a hack because IP helper API sucks */
                    if (IsReconnectHackNeeded(Adapter, &Table->table[i]))
                    {
                        /* This handles a disconnect/reconnect */

                        if (proto)
                            remove_protocol(proto);
                        Adapter->DhclientInfo.client->state = S_INIT;

                        /* These are already invalid since the media state change */
                        Adapter->RouterMib.dwForwardNextHop = 0;
                        Adapter->NteContext = 0;

                        add_protocol(Adapter->DhclientInfo.name,
                                     Adapter->DhclientInfo.rfdesc,
                                     got_one, &Adapter->DhclientInfo);
                        state_init(&Adapter->DhclientInfo);

                        SetEvent(AdapterStateChangedEvent);
                    }

                } else {
                    if (proto)
                        remove_protocol(proto);

                    /* We've lost our link so out we go */
                    RemoveEntryList(&Adapter->ListEntry);
                    free(Adapter);
                }

                ApiUnlock();

                continue;
            }

            ApiUnlock();

            Adapter = (DHCP_ADAPTER*) calloc( sizeof( DHCP_ADAPTER ) + Table->table[i].dwMtu, 1 );

            if( Adapter && Table->table[i].dwType == MIB_IF_TYPE_ETHERNET && InterfaceConnected(&Table->table[i])) {
                memcpy( &Adapter->IfMib, &Table->table[i],
                        sizeof(Adapter->IfMib) );
                Adapter->DhclientInfo.client = &Adapter->DhclientState;
                Adapter->DhclientInfo.rbuf = Adapter->recv_buf;
                Adapter->DhclientInfo.rbuf_max = Table->table[i].dwMtu;
                Adapter->DhclientInfo.rbuf_len =
                    Adapter->DhclientInfo.rbuf_offset = 0;
                memcpy(Adapter->DhclientInfo.hw_address.haddr,
                       Adapter->IfMib.bPhysAddr,
                       Adapter->IfMib.dwPhysAddrLen);
                Adapter->DhclientInfo.hw_address.hlen = Adapter->IfMib.dwPhysAddrLen;

                /* I'm not sure where else to set this, but
                   some DHCP servers won't take a zero.
                   We checked the hardware type earlier in
                   the if statement. */
                Adapter->DhclientInfo.hw_address.htype = HTYPE_ETHER;

                if( DhcpSocket == INVALID_SOCKET ) {
                    DhcpSocket =
                        Adapter->DhclientInfo.rfdesc =
                        Adapter->DhclientInfo.wfdesc =
                        socket( AF_INET, SOCK_DGRAM, IPPROTO_UDP );

                    if (DhcpSocket != INVALID_SOCKET) {
						
						/* Allow broadcast on this socket */
						Broadcast = 1;
						setsockopt(DhcpSocket,
								   SOL_SOCKET,
								   SO_BROADCAST,
								   (const char *)&Broadcast,
								   sizeof(Broadcast));
						
                        Adapter->ListenAddr.sin_family = AF_INET;
                        Adapter->ListenAddr.sin_port = htons(LOCAL_PORT);
                        Adapter->BindStatus =
                             (bind( Adapter->DhclientInfo.rfdesc,
                                    (struct sockaddr *)&Adapter->ListenAddr,
                                    sizeof(Adapter->ListenAddr) ) == 0) ?
                             0 : WSAGetLastError();
                    } else {
                        error("socket() failed: %d\n", WSAGetLastError());
                    }
                } else {
                    Adapter->DhclientInfo.rfdesc =
                        Adapter->DhclientInfo.wfdesc = DhcpSocket;
                }

                Adapter->DhclientConfig.timeout = DHCP_PANIC_TIMEOUT;
                Adapter->DhclientConfig.initial_interval = DHCP_DISCOVER_INTERVAL;
                Adapter->DhclientConfig.retry_interval = DHCP_DISCOVER_INTERVAL;
                Adapter->DhclientConfig.select_interval = 1;
                Adapter->DhclientConfig.reboot_timeout = DHCP_REBOOT_TIMEOUT;
                Adapter->DhclientConfig.backoff_cutoff = DHCP_BACKOFF_MAX;
                Adapter->DhclientState.interval =
                    Adapter->DhclientConfig.retry_interval;

                if( PrepareAdapterForService( Adapter ) ) {
                    Adapter->DhclientInfo.next = ifi;
                    ifi = &Adapter->DhclientInfo;

                    read_client_conf(&Adapter->DhclientInfo);

                    if (Adapter->DhclientInfo.client->state == S_INIT)
                    {
                        add_protocol(Adapter->DhclientInfo.name,
                                     Adapter->DhclientInfo.rfdesc,
                                     got_one, &Adapter->DhclientInfo);

                        state_init(&Adapter->DhclientInfo);
                    }

                    ApiLock();
                    InsertTailList( &AdapterList, &Adapter->ListEntry );
                    AdapterCount++;
                    SetEvent(AdapterStateChangedEvent);
                    ApiUnlock();
                } else { free( Adapter ); Adapter = 0; }
            } else { free( Adapter ); Adapter = 0; }

            if( !Adapter )
                DH_DbgPrint(MID_TRACE,("Adapter %d was rejected\n",
                                       Table->table[i].dwIndex));
        }
#if 0
        Error = NotifyAddrChange(NULL, NULL);
        if (Error != NO_ERROR)
            break;
#else
        Sleep(3000);
#endif
    } while (TRUE);

    DbgPrint("DHCPCSVC: Adapter discovery thread is terminating! (Error: %d)\n", Error);

    if( Table ) free( Table );
    return Error;
}
Beispiel #5
0
BOOL
IsReconnectHackNeeded(PDHCP_ADAPTER Adapter, const MIB_IFROW* IfEntry)
{
    struct protocol *proto;
    PIP_ADAPTER_INFO AdapterInfo, Orig;
    DWORD Size, Ret;
    char *ZeroAddress = "0.0.0.0";

    proto = find_protocol_by_adapter(&Adapter->DhclientInfo);

    if (Adapter->DhclientInfo.client->state == S_BOUND && !proto)
        return FALSE;

    if (Adapter->DhclientInfo.client->state != S_BOUND &&
        Adapter->DhclientInfo.client->state != S_STATIC)
        return FALSE;
    
    ApiUnlock();

    Orig = AdapterInfo = HeapAlloc(GetProcessHeap(), 0, sizeof(IP_ADAPTER_INFO));
    Size = sizeof(IP_ADAPTER_INFO);
    if (!AdapterInfo)
    {
        ApiLock();
        return FALSE;
    }

    Ret = GetAdaptersInfo(AdapterInfo, &Size);
    if (Ret == ERROR_BUFFER_OVERFLOW)
    {
        HeapFree(GetProcessHeap(), 0, AdapterInfo);
        AdapterInfo = HeapAlloc(GetProcessHeap(), 0, Size);
        if (!AdapterInfo)
        {
            ApiLock();
            return FALSE;
        }

        if (GetAdaptersInfo(AdapterInfo, &Size) != NO_ERROR)
        {
            ApiLock();
            return FALSE;
        }

        Orig = AdapterInfo;
        for (; AdapterInfo != NULL; AdapterInfo = AdapterInfo->Next)
        {
            if (AdapterInfo->Index == IfEntry->dwIndex)
                break;
        }

        if (AdapterInfo == NULL)
        {
            HeapFree(GetProcessHeap(), 0, Orig);
            ApiLock();
            return FALSE;
        }
    }
    else if (Ret != NO_ERROR)
    {
        HeapFree(GetProcessHeap(), 0, Orig);
        ApiLock();
        return FALSE;
    }

    if (!strcmp(AdapterInfo->IpAddressList.IpAddress.String, ZeroAddress))
    {
        HeapFree(GetProcessHeap(), 0, Orig);
        ApiLock();
        return TRUE;
    }
    else
    {
        HeapFree(GetProcessHeap(), 0, Orig);
        ApiLock();
        return FALSE;
    }
}