Пример #1
0
DWORD SrvConOpen(PWCHAR Host, PWCHAR Port, PSRV_CON *pSrvCon)
{
    SOCKET Socket;
    DWORD Err;
    ADDRINFOW Hints, *AddrInfo;
    PSRV_CON SrvCon;
    int OptVal;

    SrvCon = malloc(sizeof(*SrvCon));
    if (!SrvCon)
        return FB_E_NO_MEMORY;

    memset(SrvCon, 0, sizeof(*SrvCon));
    memset(&Hints, 0, sizeof(Hints));

    Hints.ai_family = AF_INET;
    Hints.ai_socktype = SOCK_STREAM;
    Hints.ai_protocol = IPPROTO_TCP;
    Hints.ai_flags = AI_PASSIVE;

    if (GetAddrInfoW(Host, Port, &Hints, &AddrInfo)) {
        Err = WSAGetLastError();
        printf("GetAddrInfoW failed Error %d\n", Err);
        free(SrvCon);
        return Err;
    }

    Socket = socket(AddrInfo->ai_family, AddrInfo->ai_socktype,
                    AddrInfo->ai_protocol);
    if (Socket == INVALID_SOCKET) {
        Err = WSAGetLastError();
        FreeAddrInfoW(AddrInfo);
        free(SrvCon);
        return Err;
    }

    OptVal = 1;
    if (setsockopt(Socket, SOL_SOCKET, SO_REUSEADDR,
                    (char *) &OptVal, sizeof (OptVal))) {
        Err = WSAGetLastError();
        printf("socket connect failed Error %d\n", Err);
        FreeAddrInfoW(AddrInfo);
        closesocket(Socket);
        free(SrvCon);
        return Err;
    }

    if (connect(Socket, AddrInfo->ai_addr, (int)AddrInfo->ai_addrlen)) {
        Err = WSAGetLastError();
        printf("socket connect failed Error %d\n", Err);
        FreeAddrInfoW(AddrInfo);
        closesocket(Socket);
        free(SrvCon);
        return Err;
    }

    SrvCon->Socket = Socket;
    *pSrvCon = SrvCon;
    return 0;
}
Пример #2
0
BOOL GetAddress(const WCHAR *name, INTERNET_PORT port, struct sockaddr *psa, int *sa_len, char *addr_str)
{
    ADDRINFOW *res, hints;
    void *addr = NULL;
    int ret;

    TRACE("%s\n", debugstr_w(name));

    memset( &hints, 0, sizeof(hints) );
    /* Prefer IPv4 to IPv6 addresses, since some servers do not listen on
     * their IPv6 addresses even though they have IPv6 addresses in the DNS.
     */
    hints.ai_family = AF_INET;

    ret = GetAddrInfoW(name, NULL, &hints, &res);
    if (ret != 0)
    {
        TRACE("failed to get IPv4 address of %s, retrying with IPv6\n", debugstr_w(name));
        hints.ai_family = AF_INET6;
        ret = GetAddrInfoW(name, NULL, &hints, &res);
    }
    if (ret != 0)
    {
        TRACE("failed to get address of %s\n", debugstr_w(name));
        return FALSE;
    }
    if (*sa_len < res->ai_addrlen)
    {
        WARN("address too small\n");
        FreeAddrInfoW(res);
        return FALSE;
    }
    *sa_len = res->ai_addrlen;
    memcpy( psa, res->ai_addr, res->ai_addrlen );
    /* Copy port */
    switch (res->ai_family)
    {
    case AF_INET:
        addr = &((struct sockaddr_in *)psa)->sin_addr;
        ((struct sockaddr_in *)psa)->sin_port = htons(port);
        break;
    case AF_INET6:
        addr = &((struct sockaddr_in6 *)psa)->sin6_addr;
        ((struct sockaddr_in6 *)psa)->sin6_port = htons(port);
        break;
    }

    if(addr_str)
        inet_ntop(res->ai_family, addr, addr_str, INET6_ADDRSTRLEN);
    FreeAddrInfoW(res);
    return TRUE;
}
Пример #3
0
int make_serv_sock(SERVINFO *servinfo, int servinfonum)
{
	ADDRINFOW aiwHints;
	ADDRINFOW *paiwResult;
	ADDRINFOW *paiw;
	int i;
	BOOL use = TRUE;

	ZeroMemory(&aiwHints, sizeof(aiwHints));
	if(!serv_loopback)
	{
		aiwHints.ai_flags = AI_PASSIVE;
	}
	aiwHints.ai_family = AF_UNSPEC;
	aiwHints.ai_socktype = SOCK_STREAM;
	aiwHints.ai_protocol = IPPROTO_TCP;

	if(GetAddrInfoW(nullptr, serv_port, &aiwHints, &paiwResult) != 0)
	{
		return 0;
	}

	for(i = 0, paiw = paiwResult; i < servinfonum, paiw != nullptr; paiw = paiw->ai_next)
	{
		servinfo[i].sock = socket(paiw->ai_family, paiw->ai_socktype, paiw->ai_protocol); 
		if(servinfo[i].sock == INVALID_SOCKET)
		{
			continue;
		}

		if(setsockopt(servinfo[i].sock, SOL_SOCKET, SO_REUSEADDR,
			(const char *)&use, sizeof(use)) == SOCKET_ERROR)
		{
			disconnect(servinfo[i].sock);
			continue;
		}

		if(bind(servinfo[i].sock, paiw->ai_addr, (int)paiw->ai_addrlen) == SOCKET_ERROR)
		{
			disconnect(servinfo[i].sock);
			continue;
		}

		if(listen(servinfo[i].sock, 1) == SOCKET_ERROR)
		{
			disconnect(servinfo[i].sock);
			continue;
		}

		servinfo[i].live = TRUE;
		i++;
	}

	FreeAddrInfoW(paiwResult);
	return i;
}
Пример #4
0
bool SimpleSocket::InitializeSocket(std::wstring server, std::wstring port)	{ //0 for success, 1 for error
	//Initialize the variables...Maybe not neccessary
	TheSocket = INVALID_SOCKET;
	ptr = NULL;
	result = NULL;

	int iResult;
	iResult = WSAStartup(MAKEWORD(2,2), &wsaData);
	if (iResult != 0) {
		onSysMsg(L"WSAStartup failed: %d", iResult);
		return 1;
		iStatus=SOCKET_CLOSED;
	}

	struct addrinfoW hints;
	
	ZeroMemory( &hints, sizeof(hints) );
	hints.ai_family = AF_INET;
	hints.ai_socktype = SOCK_STREAM;
	hints.ai_protocol = IPPROTO_TCP;	
	iResult = GetAddrInfoW(server.c_str(), port.c_str(), &hints, &result);

	if (iResult != 0) {
		onSysMsg(L"GetAddrInfoW failed: %d", iResult);
		WSACleanup();
		iStatus=SOCKET_CLOSED;
		return 1; 
	}	
		
	// Attempt to connect to the first address returned by
	// the call to GetAddrInfoW
	ptr=result;

	// Create a SOCKET for connecting to server
	TheSocket = socket(ptr->ai_family, ptr->ai_socktype, 
	ptr->ai_protocol);		

	if (TheSocket == INVALID_SOCKET) {
		onSysMsg(L"Error at socket(): %d", WSAGetLastError()); 
		FreeAddrInfoW(result);
		WSACleanup();
		iStatus=SOCKET_CLOSED;
		return 1; 
	}
	DWORD RCVTIMEO=15000;
	iResult = setsockopt(TheSocket, SOL_SOCKET, SO_RCVTIMEO, (char *) &RCVTIMEO, sizeof(DWORD));
	iStatus=SOCKET_INITIALIZED;
	return 0;
}
Пример #5
0
//******************************************************************************
// Routine: 
//      GetSockAddrFromString
//
// Arguments:
//      strAddress     - Address in the String format
//      pSocketAddress - Pointer to SOCKADDR_STORAGE structure where the 
//      address is returned
//
// Description:
//      Takes a string format address and returns a pointer to 
//      SOCKADDR_STORAGE structure containing the address.
//      Only resolves numeric addresses
//******************************************************************************
BOOL
GetSockAddrFromString(const WCHAR *strAddress, PSOCKADDR_STORAGE pSocketAddress)
{
    BOOL result = FALSE;    
    ADDRINFOW *pAddress = NULL;
    int wsaResult = 0;
    ADDRINFOW hints;

    ZeroMemory(&hints, sizeof(hints));
    hints.ai_family = AF_UNSPEC;
    hints.ai_flags = AI_NUMERICHOST;

    // Resolve the address
    wsaResult = GetAddrInfoW(strAddress, NULL, &hints, &pAddress);
    if (0 != wsaResult)
    {
        printf("Failed to resolve \"%S\". GetAddrInfoW() failed with 0x%x\n", strAddress, wsaResult);
        goto Exit;
    }

    // Make sure the address resolved to only one entry
    if (NULL != pAddress->ai_next)
    {
        printf("%S Resolved to more than one address. Please use a numeric Address\n", strAddress);
        goto Exit;
    }

    // Copy the address to the storage
    CopyMemory(pSocketAddress, pAddress->ai_addr, pAddress->ai_addrlen);

    result = TRUE;

Exit:
    // Cleanup
    if (NULL != pAddress)
    {
        
        FreeAddrInfoW(pAddress);
    }

    return result;
}
Пример #6
0
bool SimpleSocket::ConnectSocket() { //0 for success, 1 for error
	int iResult=SOCKET_ERROR;
	// try the next address returned by GetAddrInfoW if the connect call failed
	for(ptr=result; ptr != NULL ;ptr=ptr->ai_next) {
		iResult = connect( TheSocket, ptr->ai_addr, (int)ptr->ai_addrlen);
		/*ipv4*/
		sockaddr_in* tmp_addr=(sockaddr_in*)(ptr->ai_addr);
		unsigned char i1=(tmp_addr->sin_addr.S_un.S_un_b.s_b1);
		unsigned char i2=(tmp_addr->sin_addr.S_un.S_un_b.s_b2);
		unsigned char i3=(tmp_addr->sin_addr.S_un.S_un_b.s_b3);
		unsigned char i4=(tmp_addr->sin_addr.S_un.S_un_b.s_b4);
		wchar_t buffer[32]=L"";
		swprintf_s(buffer,32,L"%d.%d.%d.%d",i1,i2,i3,i4);
		ipv4=std::wstring(buffer);
		
		if (iResult == SOCKET_ERROR) { //ERROR
			closesocket(TheSocket);
			TheSocket = INVALID_SOCKET;
			iStatus=SOCKET_CLOSED;
		} else if (iResult == 0) { //OK
			break;
		}
	} 

	FreeAddrInfoW(result); // after success connection or tried all addrs in result, free "result"

	if (TheSocket == INVALID_SOCKET) {
		onSysMsg(L"Unable to connect to server!");
		WSACleanup();
		iStatus=SOCKET_CLOSED;
		return 1;
	}
	else {
		iStatus=SOCKET_CONNECTED;
		return 0;
	}

}
Пример #7
0
/*!
 * \brief
 * This function pings an IP-Address with a specified Time-To-Live-value.
 * 
 * \param targetIP
 * The textual representation of the IP-Address to ping (both IPv4 and IPv6 are accepted)
 * 
 * \param ttl
 * The Time-To-Live-value to perform the ping with
 * 
 * \param out
 * The Buffer into which the result of the ping-command will be written
 * 
 * \param outSize
 * The maximum number of characters that can be written into "out"
 * 
 * \returns
 * True if the execution succeded and false otherwise. The following will be written in "out": "TARGET "+TargetIP if the target was reached, "HOP "+HopIP if an intermediate Host was reached or "NO_REPLY" if an execution error occurred. If an internal error occured, a message describing that error will be written.
 *
 * \remarks
 * Writing the "ping"-function in Javascript and calling the iphlpapi.dll (and others) using c-types turned out to be impossible. The reason for that is the fact that calling GetLastError() is not possible using c-types. Therefore it is implemented in c-code and compiled into the crossbear.dll.
 * 
 */
extern "C" __declspec( dllexport ) bool ping(WCHAR * targetIP, int ttl, WCHAR * out, int  outSize){

	// Validate the Time-To-Live-Parameter: less than 1 is invalid and more than 255 doesn't make sense and might cause _itow problems
	if(ttl<1 || ttl>255){
		outPutWstring(std::wstring(L"TTL Parameter invalid"),out,outSize);
		return false;
	}

	// Verify if targetIP is a valid address if yes convert it into a addrinfo-struct
	struct addrinfoW *ai;
	if(! (0==GetAddrInfoW(targetIP,NULL,NULL,&ai))){
		outPutWstring(std::wstring(L"could not parse IP Address : ")+getFormatedLastError(),out,outSize);
		return false;
	}

	// Check if the IP-version of the targetIP is v6 ...
	if(ai->ai_family == AF_INET6){

		// ... and if it is perform a ping using ICMPv4
		return ping6(ai, ttl, out, outSize);

	}

	// Check if the IP-version of the targetIP is v4 ...
	else if(ai->ai_family == AF_INET){

		// ... and if it is perform a ping using ICMPv6
		return ping4(ai, ttl, out, outSize);

	}

	// In case the passed address is neither IPv4 nor IPv6: Return an error message
	outPutWstring(std::wstring(L"Unknown type of IPAddress"),out,outSize);
	FreeAddrInfoW(ai);
	return false;
}
Пример #8
0
int
main (int argc, char **argv)
{
    int ret;
    int r = 1;
    WSADATA wsd;
    GUID prov;
    GUID sc;
    wchar_t *cmdl;
    int wargc;
    wchar_t **wargv;

    if (WSAStartup(MAKEWORD(2,2), &wsd) != 0)
    {
        fprintf (stderr, "WSAStartup() failed: %lu\n", GetLastError());
        return 5;
    }

    cmdl = GetCommandLineW ();
    if (cmdl == NULL)
    {
        WSACleanup();
        return 2;
    }
    wargv = CommandLineToArgvW (cmdl, &wargc);
    if (wargv == NULL)
    {
        WSACleanup();
        return 3;
    }
    r = 4;

    if (wargc == 5)
    {
        if (wcscmp (wargv[1], L"A") == 0)
            sc = SVCID_DNS_TYPE_A;
        else if (wcscmp (wargv[1], L"AAAA") == 0)
            sc = SVCID_DNS_TYPE_AAAA;
        else if (wcscmp (wargv[1], L"name") == 0)
            sc = SVCID_HOSTNAME;
        else if (wcscmp (wargv[1], L"addr") == 0)
            sc = SVCID_INET_HOSTADDRBYNAME;
        else
            wargc -= 1;
        if (wcscmp (wargv[4], L"mswdns") == 0)
            prov = W32_DNS;
        else if (wcscmp (wargv[4], L"gnunetdns") == 0)
            prov = GNUNET_NAMESPACE_PROVIDER_DNS;
        else
            wargc -= 1;
    }
    else if (wargc == 3)
    {
    }
    else
    {
        fprintf (stderr, "Usage: %S <record type> <service name> <NSP library path> <NSP id>\n"
                 "record type      - one of the following: A | AAAA | name | addr\n"
                 "service name     - a string to resolve; \" \" (a space) means 'blank'\n"
                 "NSP library path - path to libw32nsp\n"
                 "NSP id           - one of the following: mswdns | gnunetdns\n",
                 wargv[0]);
    }

    if (wargc == 5)
    {
        HMODULE nsp;

        nsp = LoadLibraryW (wargv[3]);
        if (nsp == NULL)
        {
            fprintf (stderr, "Failed to load library `%S'\n", wargv[3]);
        }
        else
        {
            LPNSPSTARTUP startup = (LPNSPSTARTUP) GetProcAddress (nsp, "NSPStartup");
            if (startup == NULL)
                startup = (LPNSPSTARTUP) GetProcAddress (nsp, "NSPStartup@8");
            if (startup != NULL)
            {
                NSP_ROUTINE api;
                api.cbSize = sizeof (api);
                ret = startup (&prov, &api);
                if (NO_ERROR != ret)
                    fprintf (stderr, "startup failed: %lu\n", GetLastError ());
                else
                {
                    HANDLE lookup;
                    WSAQUERYSETW search;
                    char buf[4096];
                    WSAQUERYSETW *result = (WSAQUERYSETW *) buf;
                    DWORD resultsize;
                    DWORD err;
                    memset (&search, 0, sizeof (search));
                    search.dwSize = sizeof (search);
                    search.lpszServiceInstanceName = (wcscmp (wargv[2], L" ") == 0) ? NULL : wargv[2];
                    search.lpServiceClassId = &sc;
                    search.lpNSProviderId = &prov;
                    search.dwNameSpace = NS_ALL;
                    ret = api.NSPLookupServiceBegin (&prov, &search, NULL, LUP_RETURN_ALL, &lookup);
                    if (ret != NO_ERROR)
                    {
                        fprintf (stderr, "lookup start failed\n");
                    }
                    else
                    {
                        resultsize = 4096;
                        ret = api.NSPLookupServiceNext (lookup, LUP_RETURN_ALL, &resultsize, result);
                        err = GetLastError ();
                        if (ret != NO_ERROR)
                        {
                            fprintf (stderr, "lookup next failed: %lu\n", err);
                        }
                        else
                        {
                            int i;
                            printf ("Got result:\n");
                            printf ("  lpszServiceInstanceName: %S\n", result->lpszServiceInstanceName ? result->lpszServiceInstanceName : L"NULL");
                            if (result->lpServiceClassId)
                                printf ("  lpServiceClassId:        { 0x%08lX,0x%04X,0x%04X, { 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X } }\n",
                                        result->lpServiceClassId->Data1, result->lpServiceClassId->Data2, result->lpServiceClassId->Data3, result->lpServiceClassId->Data4[0],
                                        result->lpServiceClassId->Data4[1], result->lpServiceClassId->Data4[2], result->lpServiceClassId->Data4[3], result->lpServiceClassId->Data4[4],
                                        result->lpServiceClassId->Data4[5], result->lpServiceClassId->Data4[6], result->lpServiceClassId->Data4[7]);
                            else
                                printf ("  lpServiceClassId:        NULL\n");
                            if (result->lpVersion)
                                printf ("  lpVersion:               0x%08lX, %d\n", result->lpVersion->dwVersion, result->lpVersion->ecHow);
                            else
                                printf ("  lpVersion:               NULL\n");
                            printf ("  lpszComment:             %S\n", result->lpszComment ? result->lpszComment : L"NULL");
                            printf ("  dwNameSpace:             %lu\n", result->dwNameSpace);
                            if (result->lpNSProviderId)
                                printf ("  lpNSProviderId:          { 0x%08lX,0x%04X,0x%04X, { 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X, 0x%02X } }\n",
                                        result->lpNSProviderId->Data1, result->lpNSProviderId->Data2, result->lpNSProviderId->Data3, result->lpNSProviderId->Data4[0],
                                        result->lpNSProviderId->Data4[1], result->lpNSProviderId->Data4[2], result->lpNSProviderId->Data4[3], result->lpNSProviderId->Data4[4],
                                        result->lpNSProviderId->Data4[5], result->lpNSProviderId->Data4[6], result->lpNSProviderId->Data4[7]);
                            else
                                printf ("  lpNSProviderId:          NULL\n");
                            printf ("  lpszContext:             %S\n", result->lpszContext ? result->lpszContext : L"NULL");
                            printf ("  dwNumberOfProtocols:     %lu\n", result->dwNumberOfProtocols);
                            printf ("  lpszQueryString:         %S\n", result->lpszQueryString ? result->lpszQueryString : L"NULL");
                            printf ("  dwNumberOfCsAddrs:       %lu\n", result->dwNumberOfCsAddrs);
                            for (i = 0; i < result->dwNumberOfCsAddrs; i++)
                            {
                                switch (result->lpcsaBuffer[i].iSocketType)
                                {
                                case SOCK_STREAM:
                                    printf ("    %d: iSocketType = SOCK_STREAM\n", i);
                                    break;
                                case SOCK_DGRAM:
                                    printf ("    %d: iSocketType = SOCK_DGRAM\n", i);
                                    break;
                                default:
                                    printf ("    %d: iSocketType = %d\n", i, result->lpcsaBuffer[i].iSocketType);
                                }
                                switch (result->lpcsaBuffer[i].iProtocol)
                                {
                                case IPPROTO_TCP:
                                    printf ("    %d: iProtocol   = IPPROTO_TCP\n", i);
                                    break;
                                case IPPROTO_UDP:
                                    printf ("    %d: iProtocol   = IPPROTO_UDP\n", i);
                                    break;
                                default:
                                    printf ("    %d: iProtocol   = %d\n", i, result->lpcsaBuffer[i].iProtocol);
                                }
                                switch (result->lpcsaBuffer[i].LocalAddr.lpSockaddr->sa_family)
                                {
                                case AF_INET:
                                    printf ("    %d: loc family  = AF_INET\n", i);
                                    break;
                                case AF_INET6:
                                    printf ("    %d: loc family  = AF_INET6\n", i);
                                    break;
                                default:
                                    printf ("    %d: loc family  = %hu\n", i, result->lpcsaBuffer[i].LocalAddr.lpSockaddr->sa_family);
                                }
                                switch (result->lpcsaBuffer[i].RemoteAddr.lpSockaddr->sa_family)
                                {
                                case AF_INET:
                                    printf ("    %d: rem family  = AF_INET\n", i);
                                    break;
                                case AF_INET6:
                                    printf ("    %d: rem family  = AF_INET6\n", i);
                                    break;
                                default:
                                    printf ("    %d: rem family = %hu\n", i, result->lpcsaBuffer[i].RemoteAddr.lpSockaddr->sa_family);
                                }
                                char buf[1024];
                                DWORD buflen = 1024;
                                if (NO_ERROR == WSAAddressToStringA (result->lpcsaBuffer[i].LocalAddr.lpSockaddr, result->lpcsaBuffer[i].LocalAddr.iSockaddrLength, NULL, buf, &buflen))
                                    printf("\tLocal Address #%d: %s\n", i, buf);
                                else
                                    printf("\tLocal Address #%d: Can't convert: %lu\n", i, GetLastError ());
                                buflen = 1024;
                                if (NO_ERROR == WSAAddressToStringA (result->lpcsaBuffer[i].RemoteAddr.lpSockaddr, result->lpcsaBuffer[i].RemoteAddr.iSockaddrLength, NULL, buf, &buflen))
                                    printf("\tRemote Address #%d: %s\n", i, buf);
                                else
                                    printf("\tRemote Address #%d: Can't convert: %lu\n", i, GetLastError ());
                            }
                            printf ("  dwOutputFlags:           0x%08lX\n", result->dwOutputFlags);
                            printf ("  lpBlob:                  0x%p\n", result->lpBlob);
                            if (result->lpBlob)
                            {
                                struct hostent *he = malloc (result->lpBlob->cbSize);
                                if (he != NULL)
                                {
                                    GNUNET_memcpy (he, result->lpBlob->pBlobData, result->lpBlob->cbSize);
                                    UnpackHostEnt (he);
                                    print_hostent (he);
                                    free (he);
                                }
                            }
                        }
                        ret = api.NSPLookupServiceEnd (lookup);
                        if (ret != NO_ERROR)
                            printf ("NSPLookupServiceEnd() failed: %lu\n", GetLastError ());
                    }
                    api.NSPCleanup (&prov);
                }
            }
            FreeLibrary (nsp);
        }
    }
    else if (wargc == 3)
    {
        int s;
        ADDRINFOW hints;
        ADDRINFOW *result;
        ADDRINFOW *pos;

        memset (&hints, 0, sizeof (struct addrinfo));
        hints.ai_family = AF_UNSPEC;
        hints.ai_socktype = SOCK_STREAM;

        if (0 != (s = GetAddrInfoW (wargv[2], NULL, &hints, &result)))
        {
            fprintf (stderr, "Cound not resolve `%S' using GetAddrInfoW: %lu\n",
                     wargv[2], GetLastError ());
        }
        else
        {
            for (pos = result; pos != NULL; pos = pos->ai_next)
            {
                wchar_t tmpbuf[1024];
                DWORD buflen = 1024;
                if (0 == WSAAddressToStringW (pos->ai_addr, pos->ai_addrlen, NULL, tmpbuf, &buflen))
                    fprintf (stderr, "Result:\n"
                             "  flags: 0x%X\n"
                             "  family: 0x%X\n"
                             "  socktype: 0x%X\n"
                             "  protocol: 0x%X\n"
                             "  addrlen: %u\n"
                             "  addr: %S\n"
                             "  canonname: %S\n",
                             pos->ai_flags,
                             pos->ai_family,
                             pos->ai_socktype,
                             pos->ai_protocol,
                             pos->ai_addrlen,
                             tmpbuf,
                             pos->ai_canonname);
                else
                    fprintf (stderr, "Result:\n"
                             "  flags: 0x%X\n"
                             "  family: 0x%X\n"
                             "  socktype: 0x%X\n"
                             "  protocol: 0x%X\n"
                             "  addrlen: %u\n"
                             "  addr: %S\n"
                             "  canonname: %S\n",
                             pos->ai_flags,
                             pos->ai_family,
                             pos->ai_socktype,
                             pos->ai_protocol,
                             pos->ai_addrlen,
                             L"<can't stringify>",
                             pos->ai_canonname);
            }
            if (NULL != result)
                FreeAddrInfoW (result);
        }
    }
    WSACleanup();
    return r;
}
Пример #9
0
/*
 * Called from uv_run when complete. Call user specified callback
 * then free returned addrinfo
 * Returned addrinfo strings are converted from UTF-16 to UTF-8.
 *
 * To minimize allocation we calculate total size required,
 * and copy all structs and referenced strings into the one block.
 * Each size calculation is adjusted to avoid unaligned pointers.
 */
void uv_process_getaddrinfo_req(uv_loop_t* loop, uv_getaddrinfo_t* handle,
    uv_req_t* req) {
  int addrinfo_len = 0;
  int name_len = 0;
  size_t addrinfo_struct_len = ALIGNED_SIZE(sizeof(struct addrinfo));
  struct addrinfoW* addrinfow_ptr;
  struct addrinfo* addrinfo_ptr;
  char* alloc_ptr = NULL;
  char* cur_ptr = NULL;
  uv_err_code uv_ret;

  /* release input parameter memory */
  if (handle->alloc != NULL) {
    free(handle->alloc);
    handle->alloc = NULL;
  }

  uv_ret = uv_translate_eai_error(handle->retcode);
  if (handle->retcode == 0) {
    /* convert addrinfoW to addrinfo */
    /* first calculate required length */
    addrinfow_ptr = handle->res;
    while (addrinfow_ptr != NULL) {
      addrinfo_len += addrinfo_struct_len +
          ALIGNED_SIZE(addrinfow_ptr->ai_addrlen);
      if (addrinfow_ptr->ai_canonname != NULL) {
        name_len = uv_utf16_to_utf8(addrinfow_ptr->ai_canonname, -1, NULL, 0);
        if (name_len == 0) {
          uv_ret = uv_translate_sys_error(GetLastError());
          goto complete;
        }
        addrinfo_len += ALIGNED_SIZE(name_len);
      }
      addrinfow_ptr = addrinfow_ptr->ai_next;
    }

    /* allocate memory for addrinfo results */
    alloc_ptr = (char*)malloc(addrinfo_len);

    /* do conversions */
    if (alloc_ptr != NULL) {
      cur_ptr = alloc_ptr;
      addrinfow_ptr = handle->res;

      while (addrinfow_ptr != NULL) {
        /* copy addrinfo struct data */
        assert(cur_ptr + addrinfo_struct_len <= alloc_ptr + addrinfo_len);
        addrinfo_ptr = (struct addrinfo*)cur_ptr;
        addrinfo_ptr->ai_family = addrinfow_ptr->ai_family;
        addrinfo_ptr->ai_socktype = addrinfow_ptr->ai_socktype;
        addrinfo_ptr->ai_protocol = addrinfow_ptr->ai_protocol;
        addrinfo_ptr->ai_flags = addrinfow_ptr->ai_flags;
        addrinfo_ptr->ai_addrlen = addrinfow_ptr->ai_addrlen;
        addrinfo_ptr->ai_canonname = NULL;
        addrinfo_ptr->ai_addr = NULL;
        addrinfo_ptr->ai_next = NULL;

        cur_ptr += addrinfo_struct_len;

        /* copy sockaddr */
        if (addrinfo_ptr->ai_addrlen > 0) {
          assert(cur_ptr + addrinfo_ptr->ai_addrlen <=
                 alloc_ptr + addrinfo_len);
          memcpy(cur_ptr, addrinfow_ptr->ai_addr, addrinfo_ptr->ai_addrlen);
          addrinfo_ptr->ai_addr = (struct sockaddr*)cur_ptr;
          cur_ptr += ALIGNED_SIZE(addrinfo_ptr->ai_addrlen);
        }

        /* convert canonical name to UTF-8 */
        if (addrinfow_ptr->ai_canonname != NULL) {
          name_len = uv_utf16_to_utf8(addrinfow_ptr->ai_canonname,
                                      -1,
                                      NULL,
                                      0);
          assert(name_len > 0);
          assert(cur_ptr + name_len <= alloc_ptr + addrinfo_len);
          name_len = uv_utf16_to_utf8(addrinfow_ptr->ai_canonname,
                                      -1,
                                      cur_ptr,
                                      name_len);
          assert(name_len > 0);
          addrinfo_ptr->ai_canonname = cur_ptr;
          cur_ptr += ALIGNED_SIZE(name_len);
        }
        assert(cur_ptr <= alloc_ptr + addrinfo_len);

        /* set next ptr */
        addrinfow_ptr = addrinfow_ptr->ai_next;
        if (addrinfow_ptr != NULL) {
          addrinfo_ptr->ai_next = (struct addrinfo*)cur_ptr;
        }
      }
    } else {
      uv_ret = UV_ENOMEM;
    }

  }

  /* return memory to system */
  if (handle->res != NULL) {
    FreeAddrInfoW(handle->res);
    handle->res = NULL;
  }

complete:
  /* finally do callback with converted result */
  handle->getaddrinfo_cb(handle, uv_ret, (struct addrinfo*)alloc_ptr);

  uv_unref(loop);
}
Пример #10
0
/*
 * Called from uv_run when complete. Call user specified callback
 * then free returned addrinfo
 * Returned addrinfo strings are converted from UTF-16 to UTF-8.
 *
 * To minimize allocation we calculate total size required,
 * and copy all structs and referenced strings into the one block.
 * Each size calculation is adjusted to avoid unaligned pointers.
 */
static void uv__getaddrinfo_done(struct uv__work* w, int status) {
  uv_getaddrinfo_t* req;
  int addrinfo_len = 0;
  int name_len = 0;
  size_t addrinfo_struct_len = ALIGNED_SIZE(sizeof(struct addrinfo));
  struct addrinfoW* addrinfow_ptr;
  struct addrinfo* addrinfo_ptr;
  char* alloc_ptr = NULL;
  char* cur_ptr = NULL;

  req = container_of(w, uv_getaddrinfo_t, work_req);

  /* release input parameter memory */
  if (req->alloc != NULL) {
    free(req->alloc);
    req->alloc = NULL;
  }

  if (status == UV_ECANCELED) {
    assert(req->retcode == 0);
    req->retcode = UV_EAI_CANCELED;
    if (req->res != NULL) {
        FreeAddrInfoW(req->res);
        req->res = NULL;
    }
    goto complete;
  }

  if (req->retcode == 0) {
    /* convert addrinfoW to addrinfo */
    /* first calculate required length */
    addrinfow_ptr = req->res;
    while (addrinfow_ptr != NULL) {
      addrinfo_len += addrinfo_struct_len +
          ALIGNED_SIZE(addrinfow_ptr->ai_addrlen);
      if (addrinfow_ptr->ai_canonname != NULL) {
        name_len = uv_utf16_to_utf8(addrinfow_ptr->ai_canonname, -1, NULL, 0);
        if (name_len == 0) {
          req->retcode = uv_translate_sys_error(GetLastError());
          goto complete;
        }
        addrinfo_len += ALIGNED_SIZE(name_len);
      }
      addrinfow_ptr = addrinfow_ptr->ai_next;
    }

    /* allocate memory for addrinfo results */
    alloc_ptr = (char*)malloc(addrinfo_len);

    /* do conversions */
    if (alloc_ptr != NULL) {
      cur_ptr = alloc_ptr;
      addrinfow_ptr = req->res;

      while (addrinfow_ptr != NULL) {
        /* copy addrinfo struct data */
        assert(cur_ptr + addrinfo_struct_len <= alloc_ptr + addrinfo_len);
        addrinfo_ptr = (struct addrinfo*)cur_ptr;
        addrinfo_ptr->ai_family = addrinfow_ptr->ai_family;
        addrinfo_ptr->ai_socktype = addrinfow_ptr->ai_socktype;
        addrinfo_ptr->ai_protocol = addrinfow_ptr->ai_protocol;
        addrinfo_ptr->ai_flags = addrinfow_ptr->ai_flags;
        addrinfo_ptr->ai_addrlen = addrinfow_ptr->ai_addrlen;
        addrinfo_ptr->ai_canonname = NULL;
        addrinfo_ptr->ai_addr = NULL;
        addrinfo_ptr->ai_next = NULL;

        cur_ptr += addrinfo_struct_len;

        /* copy sockaddr */
        if (addrinfo_ptr->ai_addrlen > 0) {
          assert(cur_ptr + addrinfo_ptr->ai_addrlen <=
                 alloc_ptr + addrinfo_len);
          memcpy(cur_ptr, addrinfow_ptr->ai_addr, addrinfo_ptr->ai_addrlen);
          addrinfo_ptr->ai_addr = (struct sockaddr*)cur_ptr;
          cur_ptr += ALIGNED_SIZE(addrinfo_ptr->ai_addrlen);
        }

        /* convert canonical name to UTF-8 */
        if (addrinfow_ptr->ai_canonname != NULL) {
          name_len = uv_utf16_to_utf8(addrinfow_ptr->ai_canonname,
                                      -1,
                                      NULL,
                                      0);
          assert(name_len > 0);
          assert(cur_ptr + name_len <= alloc_ptr + addrinfo_len);
          name_len = uv_utf16_to_utf8(addrinfow_ptr->ai_canonname,
                                      -1,
                                      cur_ptr,
                                      name_len);
          assert(name_len > 0);
          addrinfo_ptr->ai_canonname = cur_ptr;
          cur_ptr += ALIGNED_SIZE(name_len);
        }
        assert(cur_ptr <= alloc_ptr + addrinfo_len);

        /* set next ptr */
        addrinfow_ptr = addrinfow_ptr->ai_next;
        if (addrinfow_ptr != NULL) {
          addrinfo_ptr->ai_next = (struct addrinfo*)cur_ptr;
        }
      }
    } else {
      req->retcode = UV_EAI_MEMORY;
    }
  }

  /* return memory to system */
  if (req->res != NULL) {
    FreeAddrInfoW(req->res);
    req->res = NULL;
  }

complete:
  uv__req_unregister(req->loop, req);

  /* finally do callback with converted result */
  req->getaddrinfo_cb(req, req->retcode, (struct addrinfo*)alloc_ptr);
}
Пример #11
0
__declspec(dllexport) BOOL SoaronModuleFunc(void)
{
	SQLHDBC  hdbc;
	HSTMT hstmt;
	unsigned int NumOfLinks, LinkID;
	WSADATA wd;
	SQLRETURN sqlret;
	HANDLE hHeap;
	FTNAddr LinkAddr;
	wchar_t Ip[256];

	lpLinksCheckInfo LinksTable;
	WSAEVENT * EventsTable;
	WSANETWORKEVENTS evt;
	unsigned int i, j;
	int res;

	ADDRINFOW *result = NULL;
	ADDRINFOW hints;
	wchar_t LogStr[255];
	memset(&hints, 0, sizeof(hints));

	LinkAddr.point = 0;
	NumOfLinks = 0;
	SQLAllocHandle(SQL_HANDLE_DBC, cfg.henv, &hdbc);
	sqlret = SQLDriverConnectW(hdbc, NULL, cfg.ConnectionString, SQL_NTS, NULL, 0, NULL, SQL_DRIVER_NOPROMPT);
	if (sqlret != SQL_SUCCESS && sqlret != SQL_SUCCESS_WITH_INFO)
	{
		SetEvent(cfg.hExitEvent); return FALSE;//fatal error
	}
	SQLAllocHandle(SQL_HANDLE_STMT, hdbc, &hstmt);

	AddLogEntry(L"Checking binkp links alive");
	//get links info
	SQLExecDirectW(hstmt, L"update Links set DialOut=0 where datediff(minute,LastSessionTime,GetDate())>40 and LinkType=1", SQL_NTS);
	sqlret = SQLExecDirectW(hstmt, L"select count(*) from Links where dialout=0 and passivelink=0 and LinkType=1 and isnull(ip,'')<>''", SQL_NTS);
	if ((sqlret == SQL_SUCCESS) || (sqlret = SQL_SUCCESS_WITH_INFO))
	{
		sqlret = SQLFetch(hstmt);
		if ((sqlret == SQL_SUCCESS) || (sqlret = SQL_SUCCESS_WITH_INFO))
		{
			SQLGetData(hstmt, 1, SQL_C_ULONG, &NumOfLinks, 0, NULL);
		}
	}
	SQLCloseCursor(hstmt);
	if (NumOfLinks == 0) goto exit;
	hHeap = HeapCreate(HEAP_NO_SERIALIZE, 8192, 0);
	LinksTable = HeapAlloc(hHeap, HEAP_ZERO_MEMORY, NumOfLinks*sizeof(LinksCheckInfo));
	EventsTable = HeapAlloc(hHeap, HEAP_ZERO_MEMORY, sizeof(WSAEVENT)*NumOfLinks);
	i = 0;
	hints.ai_family = AF_INET;
	hints.ai_socktype = SOCK_STREAM;
	hints.ai_protocol = IPPROTO_TCP;


	WSAStartup(MAKEWORD(2, 2), &wd);
	sqlret = SQLExecDirectW(hstmt, L"select LinkID,Zone,Net,Node, Ip from Links where dialout=0 and passivelink=0 and LinkType=1 and isnull(ip,'')<>''", SQL_NTS);
	if ((sqlret == SQL_SUCCESS) || (sqlret = SQL_SUCCESS_WITH_INFO))
	{
		
		SQLBindCol(hstmt, 1, SQL_C_ULONG, &LinkID, 0, NULL);
		SQLBindCol(hstmt, 2, SQL_C_USHORT, &(LinkAddr.zone), 0, NULL);
		SQLBindCol(hstmt, 3, SQL_C_USHORT, &(LinkAddr.net), 0, NULL);
		SQLBindCol(hstmt, 4, SQL_C_USHORT, &(LinkAddr.node), 0, NULL);
		SQLBindCol(hstmt, 5, SQL_C_WCHAR, Ip, 512, NULL);
		sqlret = SQLFetch(hstmt);
		while ((sqlret == SQL_SUCCESS) || (sqlret == SQL_SUCCESS_WITH_INFO))
		{
			//


			res = GetAddrInfoW(Ip, L"24554", &hints, &result);
			if (res == 0)
			{

				memcpy(&(LinksTable[i].sa), result->ai_addr, sizeof(struct sockaddr_in));
				//				printf("%u  %u %S %u.%u.%u.%u\n", i,LinkID, Ip, LinksTable[i].sa.sin_addr.S_un.S_un_b.s_b1, LinksTable[i].sa.sin_addr.S_un.S_un_b.s_b2, LinksTable[i].sa.sin_addr.S_un.S_un_b.s_b3, LinksTable[i].sa.sin_addr.S_un.S_un_b.s_b4);

				LinksTable[i].LinkID = LinkID;
				LinksTable[i].LinkAddr.FullAddr = LinkAddr.FullAddr;
				LinksTable[i].s = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
				EventsTable[i] = WSACreateEvent();
				WSAEventSelect(LinksTable[i].s, EventsTable[i], FD_CONNECT);
				FreeAddrInfoW(result);
				++i;
			}
			else
			{
				wsprintfW(LogStr,L"%u:%u/%u: Ip address %s cannot be resolved", LinkAddr.zone, LinkAddr.net, LinkAddr.node,Ip);
				AddLogEntry(LogStr);
			}


			sqlret = SQLFetch(hstmt);

		}

	}
	SQLCloseCursor(hstmt);
	SQLFreeStmt(hstmt, SQL_UNBIND);
	NumOfLinks = i;
	for (i = 0; i < NumOfLinks; i++)
	{
		connect(LinksTable[i].s, (struct sockaddr *)&(LinksTable[i].sa), sizeof(struct sockaddr_in));
	}
	j = 0;

	SQLBindParameter(hstmt, 1, SQL_PARAM_INPUT, SQL_C_ULONG, SQL_INTEGER, 0, 0, &LinkID, 0, NULL);
	SQLPrepareW(hstmt, L"Update Links set DialOut=1 where LinkID=?", SQL_NTS);

	while (j < NumOfLinks)
	{
		res = WSAWaitForMultipleEvents(NumOfLinks, EventsTable, FALSE, WSA_INFINITE, FALSE);
		WSAEnumNetworkEvents(LinksTable[res].s, EventsTable[res], &evt);
		shutdown(LinksTable[res].s, SD_BOTH);
		closesocket(LinksTable[res].s);
		if (evt.iErrorCode[FD_CONNECT_BIT] == 0)
		{
			wsprintfW(LogStr, L"%u:%u/%u: OK", LinksTable[res].LinkAddr.zone, LinksTable[res].LinkAddr.net, LinksTable[res].LinkAddr.node);
			LinkID = LinksTable[res].LinkID;
			SQLExecute(hstmt);
		}
		else
		{
			switch (evt.iErrorCode[FD_CONNECT_BIT])
			{
				case WSAECONNREFUSED:
					wsprintfW(LogStr, L"%u:%u/%u: Connection refused", LinksTable[res].LinkAddr.zone, LinksTable[res].LinkAddr.net, LinksTable[res].LinkAddr.node);
					break;
				case WSAETIMEDOUT:
					wsprintfW(LogStr, L"%u:%u/%u: Connection timed out", LinksTable[res].LinkAddr.zone, LinksTable[res].LinkAddr.net, LinksTable[res].LinkAddr.node);
					break;
				default:wsprintfW(LogStr, L"%u:%u/%u: Unknown connection error", LinksTable[res].LinkAddr.zone, LinksTable[res].LinkAddr.net, LinksTable[res].LinkAddr.node);

			
			}

		}
		AddLogEntry(LogStr);
		++j;
	}
	//

	for (j = 0; j < NumOfLinks; j++)
	{
		WSACloseEvent(EventsTable[j]);
	}
	SQLFreeStmt(hstmt, SQL_RESET_PARAMS);
	//
	WSACleanup();
	HeapDestroy(hHeap);
exit:
	SQLFreeHandle(SQL_HANDLE_STMT, hstmt);
	SQLDisconnect(hdbc);
	SQLFreeHandle(SQL_HANDLE_DBC, hdbc);
	AddLogEntry(L"Links alive check done");
	SetEvent(cfg.hLinksUpdateEvent);
	return TRUE;
}
Пример #12
0
/*!
 * \brief
 * This function pings an IPv4-Address with a specified Time-To-Live-value.
 * 
 * \param ai
 * The AddrInfo-representation of the TargetIP
 * 
 * \param ttl
 * The Time-To-Live-value to perform the ping with
 * 
 * \param out
 * The Buffer into which the result of the ping-command will be written
 * 
 * \param outSize
 * The maximum number of characters that can be written into "out"
 * 
 * \returns
 * True if the execution succeded and false otherwise. The following will be written in "out": "TARGET "+TargetIP if the target was reached, "HOP "+HopIP if an intermediate Host was reached or "NO_REPLY" if an execution error occurred. If an internal error occured, a message describing that error will be written.
 *
 * \remarks
 * ai will be Freed
 */
bool ping4(struct addrinfoW *ai, int ttl, WCHAR * out, int  outSize){
	
		// Create a handle to a hIcmpFile (required by IcmpSendEcho2)
		HANDLE hIcmpFile = IcmpCreateFile();
		if (hIcmpFile == INVALID_HANDLE_VALUE) {
			outPutWstring(std::wstring(L"IcmpCreatefile returned error: ")+getFormatedLastError(),out,outSize);

			// Free all allocated resources
			FreeAddrInfoW(ai);
			return false;
		}

		// Build the payload of the ICMP-request (mustn't be empty)
		char SendData[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ012345";

		// Allocate space for a single reply
		DWORD ReplySize = sizeof (ICMP_ECHO_REPLY) + sizeof (SendData) + 8 + sizeof(IO_STATUS_BLOCK);
		LPVOID ReplyBuffer = (VOID *) malloc(ReplySize);

		// Convert the IP-Address into the correct format
		IPAddr ipaddr;
		memcpy(&ipaddr, &((sockaddr_in *)ai->ai_addr)->sin_addr, sizeof(ipaddr));

		// Create a IP_OPTION_INFORMATION and set its TTL-field so IcmpSendEcho2 will perform a ping with the correct TTL
		IP_OPTION_INFORMATION ipopts;
		memset(&ipopts,0,sizeof(ipopts));
		ipopts.Ttl = (unsigned char)ttl;

		//Try to perform the actual ping
		DWORD dwRetVal = IcmpSendEcho2(hIcmpFile, NULL, NULL, NULL,  ipaddr, SendData, sizeof (SendData), &ipopts, ReplyBuffer, ReplySize, 1000);
		if (dwRetVal == 0) {

			// In case it failed: Did it fail because of a timeout or because of a serious problem?
			bool success = false;
			DWORD lastError = GetLastError();
			if(IP_REQ_TIMED_OUT == lastError || IP_DEST_NET_UNREACHABLE ==  lastError ){
				// If it failed because of a Timeout return "NO_REPLY"
				outPutWstring(std::wstring(L"NO_REPLY"),out,outSize);
				success = true;
			}
			else{
				// If it failed because of a serious problem return a detailed description about the failure
				outPutWstring(std::wstring(L"Call to IcmpSendEcho2 failed: ")+getFormatedLastError(),out,outSize);
			}

			// Free all allocated resources
			FreeAddrInfoW(ai);
			free(ReplyBuffer);
			IcmpCloseHandle(hIcmpFile);
			return success;
		}

		// Parse the reply on the ICMP-request
		PICMP_ECHO_REPLY pEchoReply = (PICMP_ECHO_REPLY) ReplyBuffer;

		// Extract the address of the replying host
		struct in_addr ReplyAddr;
		ReplyAddr.S_un.S_addr = pEchoReply->Address;
		std::wstring hopName = s2ws(std::string(inet_ntoa(ReplyAddr)));

		// Switch according to status of reply
		ULONG status = pEchoReply->Status;

		if(status == IP_SUCCESS){
			// Ping reached the target
			outPutWstring(std::wstring(L"TARGET ")+ hopName,out,outSize);
		}
		else if(status == IP_TTL_EXPIRED_TRANSIT || status == IP_TTL_EXPIRED_REASSEM){
			// Ping got a reply from a hop on the way to target
			outPutWstring(std::wstring(L"HOP ")+ hopName,out,outSize);
		}
		else{
			// Something didn't work
			outPutWstring(std::wstring(L"NO_REPLY"),out,outSize);
		}

		// Free all allocated resources
		free(ReplyBuffer);
		FreeAddrInfoW(ai);
		IcmpCloseHandle(hIcmpFile);
		return true;

}
Пример #13
0
/*!
 * \brief
 * This function pings an IPv6-Address with a specified Time-To-Live-value.
 * 
 * \param ai
 * The AddrInfo-representation of the TargetIP
 * 
 * \param ttl
 * The Time-To-Live-value to perform the ping with
 * 
 * \param out
 * The Buffer into which the result of the ping-command will be written
 * 
 * \param outSize
 * The maximum number of characters that can be written into "out"
 * 
 * \returns
 * True if the execution succeded and false otherwise. The following will be written in "out": "TARGET "+TargetIP if the target was reached, "HOP "+HopIP if an intermediate Host was reached or "NO_REPLY" if an execution error occurred. If an internal error occured, a message describing that error will be written.
 *
 * \remarks
 * ai will be Freed
 */
bool ping6(struct addrinfoW *ai, int ttl, WCHAR * out, int  outSize){
	// Create a handle to a hIcmpFile (required by Icmp6SendEcho2)
		HANDLE hIcmpFile = Icmp6CreateFile();
		if (hIcmpFile == INVALID_HANDLE_VALUE) {
			outPutWstring(std::wstring(L"Icmp6Createfile returned error: ")+getFormatedLastError(),out,outSize);

			// Free all allocated resources
			FreeAddrInfoW(ai);
			return false;
		}

		// A ICMP-request using IPv6 requires a source address: Get the system's IPv6 addresses
		ADDRINFOW hints;
		memset(&hints,0,sizeof(ADDRINFOW));
		hints.ai_family = AF_INET6;
		struct addrinfoW *lai;
		if(! (0==GetAddrInfoW(L"",NULL,&hints,&lai))){
			outPutWstring(std::wstring(L"Invalid Socket (Localhost) : ")+getFormatedLastError(),out,outSize);

			// Free all allocated resources
			FreeAddrInfoW(ai);
			IcmpCloseHandle(hIcmpFile);
			return false;
		}

		// Out of all of the system's IPv6-addresses: get a global IPv6 IP-Address for localhost
		struct addrinfoW *sourceGlobal = lai;
		while(sourceGlobal != NULL){
			sockaddr_in6 * a = (sockaddr_in6 *)sourceGlobal->ai_addr;
			if(IN6_IS_ADDR_GLOBAL(&a->sin6_addr)) break;
			sourceGlobal = sourceGlobal->ai_next;
		}

		// If there is none then there is no way to perform an ICMP-request on a IPv6-address -> abbort!
		if(sourceGlobal == NULL){
			outPutWstring(std::wstring(L"No global IPv6 interface found on localhost: ")+getFormatedLastError(),out,outSize);

			// Free all allocated resources
			FreeAddrInfoW(ai);
			FreeAddrInfoW(lai);
			IcmpCloseHandle(hIcmpFile);
			return false;
		}


		// Build the payload of the ICMP-request (mustn't be empty)
		char SendData[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ012345";

		// Allocate space for a single reply
		DWORD ReplySize = sizeof (ICMPV6_ECHO_REPLY) + sizeof (SendData) + 8 + sizeof(IO_STATUS_BLOCK);
		LPVOID ReplyBuffer = (VOID *) malloc(ReplySize);

		// Create a IP_OPTION_INFORMATION and set its TTL-field so Icmp6SendEcho2 will perform a ping with the correct TTL
		IP_OPTION_INFORMATION ipopts;
		memset(&ipopts,0,sizeof(ipopts));
		ipopts.Ttl = (unsigned char)ttl;

		//Try to perform the actual ping
		DWORD dwRetVal = Icmp6SendEcho2(hIcmpFile, NULL, NULL, NULL,(sockaddr_in6 *)sourceGlobal->ai_addr,  (sockaddr_in6 *)ai->ai_addr, SendData, sizeof (SendData), &ipopts, ReplyBuffer, ReplySize, 1000);
		if (dwRetVal == 0) {

			// In case it failed: Did it fail because of a timeout or because of a serious problem?
			bool success = false;
			DWORD lastError = GetLastError();
			if(IP_REQ_TIMED_OUT == lastError || IP_DEST_NET_UNREACHABLE ==  lastError ){
				// If it failed because of a Timeout return "NO_REPLY"
				outPutWstring(std::wstring(L"NO_REPLY"),out,outSize);
				success = true;
			}
			else{
				// If it failed because of a serious problem return a detailed description about the failure
				outPutWstring(std::wstring(L"Call to Icmp6SendEcho2 failed: ")+getFormatedLastError(),out,outSize);
			}

			// Free all allocated resources
			FreeAddrInfoW(ai);
			FreeAddrInfoW(lai);
			free(ReplyBuffer);
			IcmpCloseHandle(hIcmpFile);
			return success;
		}

		// Parse the reply on the ICMP-request
		PICMPV6_ECHO_REPLY pEchoReply = (PICMPV6_ECHO_REPLY) ReplyBuffer;

		/*
		 * Extract the address of the replying host
		 */
		// First: copy the reply data into a sockaddr_in6-struckture
		PIPV6_ADDRESS_EX pIP6Addr = &pEchoReply->Address;;
		sockaddr_in6 sock6;
		sock6.sin6_family = AF_INET6;
		sock6.sin6_flowinfo = pIP6Addr->sin6_flowinfo;
		sock6.sin6_port = pIP6Addr->sin6_port;
		sock6.sin6_scope_id = pIP6Addr->sin6_scope_id;
		memcpy(&sock6.sin6_addr, pIP6Addr->sin6_addr,sizeof(IN6_ADDR));

		// Second: convert it into human readable version
		WCHAR  ip6AddressString[256];
		DWORD bufferLenght = 256;
		if(0 != WSAAddressToStringW((LPSOCKADDR)&sock6,sizeof(sockaddr_in6),NULL,ip6AddressString,&bufferLenght)){
			outPutWstring(std::wstring(L"Call to WSAAddressToStringW failed: ")+getFormatedLastError(),out,outSize);

			// Free all allocated resources
			FreeAddrInfoW(ai);
			FreeAddrInfoW(lai);
			free(ReplyBuffer);
			IcmpCloseHandle(hIcmpFile);
			return false;
		}

		// Third: convert it into a wstring
		std::wstring hopName = std::wstring(ip6AddressString);

		/*
		 * Switch according to status of reply
		 */
		ULONG status = pEchoReply->Status;

		if(status == IP_SUCCESS){ 
			// Ping reached the target
			outPutWstring(std::wstring(L"TARGET ")+ hopName,out,outSize);
		}
		else if(status == IP_TTL_EXPIRED_TRANSIT || status == IP_TTL_EXPIRED_REASSEM){ 
			// Ping got a reply from a hop on the way to target
			outPutWstring(std::wstring(L"HOP ")+ hopName,out,outSize);
		}
		else{ 
			// Something didn't work
			outPutWstring(std::wstring(L"NO_REPLY"),out,outSize);
		}

		// Free all allocated resources
		free(ReplyBuffer);
		FreeAddrInfoW(ai);
		FreeAddrInfoW(lai);
		IcmpCloseHandle(hIcmpFile);
		return true;
}
Пример #14
0
int
wmain(int argc, WCHAR *argv[])
{
    WSADATA wsaData;
    ULONG i;
    DWORD StrLen = 46;
    int Status;

    /* Initialize the Console Standard Streams */
    ConInitStdStreams();

    IpOptions.Ttl = 128;

    if (!ParseCmdLine(argc, argv))
        return 1;

    if (!SetConsoleCtrlHandler(ConsoleCtrlHandler, TRUE))
    {
        DPRINT("Failed to set control handler: %lu\n", GetLastError());
        return 1;
    }

    Status = WSAStartup(MAKEWORD(2, 2), &wsaData);
    if (Status != 0)
    {
        ConResPrintf(StdErr, IDS_WINSOCK_FAIL, Status);
        return 1;
    }

    if (!ResolveTarget(TargetName))
    {
        WSACleanup();
        return 1;
    }

    if (WSAAddressToStringW(Target->ai_addr, (DWORD)Target->ai_addrlen, NULL, Address, &StrLen) != 0)
    {
        DPRINT("WSAAddressToStringW failed: %d\n", WSAGetLastError());
        FreeAddrInfoW(Target);
        WSACleanup();
        return 1;
    }

    if (Family == AF_INET6)
        hIcmpFile = Icmp6CreateFile();
    else
        hIcmpFile = IcmpCreateFile();


    if (hIcmpFile == INVALID_HANDLE_VALUE)
    {
        DPRINT("IcmpCreateFile failed: %lu\n", GetLastError());
        FreeAddrInfoW(Target);
        WSACleanup();
        return 1;
    }

    if (*CanonName)
        ConResPrintf(StdOut, IDS_PINGING_HOSTNAME, CanonName, Address);
    else
        ConResPrintf(StdOut, IDS_PINGING_ADDRESS, Address);

    ConResPrintf(StdOut, IDS_PING_SIZE, RequestSize);

    Ping();

    i = 1;
    while (i < PingCount)
    {
        Sleep(1000);
        Ping();

        if (!PingForever)
            i++;
    }

    PrintStats();

    IcmpCloseHandle(hIcmpFile);
    FreeAddrInfoW(Target);
    WSACleanup();

    return 0;
}
Пример #15
0
void ConnectSKKServer()
{
	ADDRINFOW *paiwResult;
	ADDRINFOW *paiw;
	u_long mode;
	timeval tv;
	fd_set fdw, fde;

	ADDRINFOW aiwHints = {};
	aiwHints.ai_family = AF_UNSPEC;
	aiwHints.ai_socktype = SOCK_STREAM;
	aiwHints.ai_protocol = IPPROTO_TCP;

	if(GetAddrInfoW(host, port, &aiwHints, &paiwResult) != 0)
	{
		return;
	}

	for(paiw = paiwResult; paiw != nullptr; paiw = paiw->ai_next)
	{
		sock = socket(paiw->ai_family, paiw->ai_socktype, paiw->ai_protocol);
		if(sock == INVALID_SOCKET)
		{
			continue;
		}

		if(setsockopt(sock, SOL_SOCKET, SO_SNDTIMEO, (const char*)&timeout, sizeof(timeout)) == SOCKET_ERROR)
		{
			closesocket(sock);
			sock = INVALID_SOCKET;
			continue;
		}
		if(setsockopt(sock, SOL_SOCKET, SO_RCVTIMEO, (const char*)&timeout, sizeof(timeout)) == SOCKET_ERROR)
		{
			closesocket(sock);
			sock = INVALID_SOCKET;
			continue;
		}

		mode = 1;
		ioctlsocket(sock, FIONBIO, &mode);

		if(connect(sock, paiw->ai_addr, (int)paiw->ai_addrlen) == SOCKET_ERROR)
		{
			if(WSAGetLastError() != WSAEWOULDBLOCK)
			{
				closesocket(sock);
				sock = INVALID_SOCKET;
				continue;
			}
		}

		mode = 0;
		ioctlsocket(sock, FIONBIO, &mode);

		tv.tv_sec = timeout / 1000;
		tv.tv_usec = (timeout % 1000) * 1000;

		FD_ZERO(&fdw);
		FD_ZERO(&fde);
		FD_SET(sock, &fdw);
		FD_SET(sock, &fde);

		select(0, nullptr, &fdw, &fde, &tv);
		if(FD_ISSET(sock, &fdw))
		{
			break;
		}

		DisconnectSKKServer();
	}

	FreeAddrInfoW(paiwResult);
}
Пример #16
0
/*
 * @implemented
 */
INT
WSAAPI
GetAddrInfoW(IN PCWSTR pszNodeName,
             IN PCWSTR pszServiceName,
             IN const ADDRINFOW *ptHints,
             OUT PADDRINFOW *pptResult)
{
    INT iError = 0;
    INT iFlags = 0;
    INT iFamily = PF_UNSPEC;
    INT iSocketType = 0;
    INT iProtocol = 0;
    WORD wPort = 0;
    DWORD dwAddress = 0;
    PSERVENT ptService = NULL;
    PCHAR pc = NULL;
    BOOL bClone = FALSE;
    WORD wTcpPort = 0;
    WORD wUdpPort = 0;
    WCHAR CanonicalName[0x42];
    CHAR AnsiServiceName[256];
    CHAR AnsiNodeName[256];
    DPRINT("GetAddrInfoW: %S, %S, %p, %p\n", pszNodeName, pszServiceName, ptHints, pptResult);

    /* Assume error */
    *pptResult  = NULL;

    /* We must have at least one name to work with */
    if (!(pszNodeName) && !(pszServiceName))
    {
        /* Fail */
        SetLastError(EAI_NONAME);
        return EAI_NONAME;
    }

    /* Check if we got hints */
    if (ptHints)
    {
        /* Make sure these are empty */
        if ((ptHints->ai_addrlen) ||
            (ptHints->ai_canonname) ||
            (ptHints->ai_addr) ||
            (ptHints->ai_next))
        {
            /* Fail if they aren't */
            SetLastError(EAI_FAIL);
            return EAI_FAIL;
        }
        
        /* Save the flags and validate them */
        iFlags = ptHints->ai_flags;
        if ((iFlags & AI_CANONNAME) && !pszNodeName)
        {
            SetLastError(EAI_BADFLAGS);
            return EAI_BADFLAGS;
        }

        /* Save family and validate it */
        iFamily = ptHints->ai_family;
        if ((iFamily != PF_UNSPEC) && (iFamily != PF_INET))
        {
            SetLastError(EAI_FAMILY);
            return EAI_FAMILY;
        }

        /* Save socket type and validate it */
        iSocketType = ptHints->ai_socktype;
        if ((iSocketType != 0) &&
            (iSocketType != SOCK_STREAM) &&
            (iSocketType != SOCK_DGRAM) &&
            (iSocketType != SOCK_RAW))
        {
            SetLastError(EAI_SOCKTYPE);
            return EAI_SOCKTYPE;
        }

        /* Save the protocol */
        iProtocol = ptHints->ai_protocol;
    }

    /* Check if we have a service name */
    if (pszServiceName)
    {
        /* We need to convert it to ANSI */
        WideCharToMultiByte(CP_ACP,
                            0,
                            pszServiceName, 
                            -1, 
                            AnsiServiceName, 
                            sizeof(AnsiServiceName),
                            NULL,
                            0);

        /* Get the port */
        wPort = (WORD)strtoul(AnsiServiceName, &pc, 10);

        /* Check if the port string is numeric */
        if (*pc == '\0')
        {
            /* Get the port directly */
            wPort = wTcpPort = wUdpPort = htons(wPort);

#if 0
            /* Check if this is both TCP and UDP */
            if (iSocketType == 0)
            {
                /* Set it to TCP for now, but remember to clone */
                bClone = TRUE;
                iSocketType = SOCK_STREAM;
            }
#endif
        }
        else
        {
            wPort = 0;
            /* The port name was a string. Check if this is a UDP socket */
            if ((iSocketType == 0) || (iSocketType == SOCK_DGRAM))
            {
                /* It's UDP, do a getservbyname */
                ptService = getservbyname(AnsiServiceName, "udp");

                /* If we got a servent, return the port from it */
                if (ptService) wPort = wUdpPort = ptService->s_port;
            }

            /* Check if this is a TCP socket */
            if ((iSocketType == 0) || (iSocketType == SOCK_STREAM))
            {
                /* It's TCP, do a getserbyname */
                ptService = getservbyname(AnsiServiceName, "tcp");

                /* Return the port from the servent */
                if (ptService) wPort = wTcpPort = ptService->s_port;
            }
            
            /* If we got 0, then fail */
            if (wPort == 0)
            {
                SetLastError(EAI_SERVICE);
                return EAI_SERVICE;
            }

            /* Check if this was for both */
            if (iSocketType == 0)
            {
                /* Do the TCP case right now */
                if (wTcpPort && !wUdpPort)
                    iSocketType = SOCK_STREAM;
                if (!wTcpPort && wUdpPort)
                    iSocketType = SOCK_DGRAM;
                //bClone = (wTcpPort && wUdpPort); 
            }
        }
    }

    /* Check if no node was given or if this is is a valid IPv4 address */
    if ((!pszNodeName) || (ParseV4Address(pszNodeName, &dwAddress)))
    {
        /* Check if we don't have a node name */
        if (!pszNodeName)
        {
            /* Make one up based on the flags */
            dwAddress = htonl((iFlags & AI_PASSIVE) ?
                              INADDR_ANY : INADDR_LOOPBACK);
        }
        
        /* Create the Addr Info */
        *pptResult = NewAddrInfo(iSocketType, iProtocol, wPort, dwAddress);

        /* If we didn't get one back, assume out of memory */
        if (!(*pptResult)) iError = EAI_MEMORY;
        
        /* Check if we have success and a nodename */
        if (!iError && pszNodeName)
        {
            /* Set AI_NUMERICHOST since this is a numeric string */
            (*pptResult)->ai_flags |= AI_NUMERICHOST;
            
            /* Check if the canonical name was requested */
            if (iFlags & AI_CANONNAME)
            {
                /* Get the canonical name */
                GetNameInfoW((*pptResult)->ai_addr,
                             (socklen_t)(*pptResult)->ai_addrlen,
                             CanonicalName,
                             0x41,
                             NULL,
                             0,
                             2);

                /* Allocate memory for a copy */
                (*pptResult)->ai_canonname = HeapAlloc(WsSockHeap,
                                                       0,
                                                       wcslen(CanonicalName));
                
                if (!(*pptResult)->ai_canonname)
                {
                    /* No memory for the copy */
                    iError = EAI_MEMORY;
                }
                else
                {
                    /* Duplicate the string */
                    RtlMoveMemory((*pptResult)->ai_canonname,
                                  CanonicalName,
                                  wcslen(CanonicalName));
                }
            }
        }
    }
    else if (iFlags & AI_NUMERICHOST)
    {
        /* No name for this request (we have a non-numeric name) */
        iError = EAI_NONAME;
    }
    else
    {
        /* We need to convert it to ANSI */
        WideCharToMultiByte(CP_ACP,
                            0,
                            pszNodeName, 
                            -1, 
                            AnsiNodeName, 
                            sizeof(AnsiNodeName),
                            NULL,
                            0);

        /* Non-numeric name, do DNS lookup */
        iError = LookupAddressForName(AnsiNodeName,
                                      iSocketType,
                                      iProtocol,
                                      wPort,
                                      (iFlags & AI_CANONNAME),
                                      pptResult);
    }

    /* If all was good and the caller requested UDP and TCP */
    if (!iError && bClone)
    {
        /* Process UDP now, we already did TCP */
        iError = CloneAddrInfo(wUdpPort, *pptResult);
    }

    /* If we've hit an error till here */
    if (iError)
    {
        /* Free the address info and return nothing */
        FreeAddrInfoW(*pptResult);
        *pptResult = NULL;        
    }

    /* Return to caller */
    SetLastError(iError);
    return iError;
}