Скачать файл с интернета по прямой ссылке - C (СИ)

Узнай цену своей работы

Формулировка задачи:

появилась необходимость в скачивании файла с инета по прямой ссылке, но к сажелению в инете на СИ ненашел,очень надеюсь на вашу помощь. (например скачать test.txt файл с mysite.ru/test.txt)

Решение задачи: «Скачать файл с интернета по прямой ссылке»

textual
Листинг программы
// by SlyBit (c) 07.2008 /DownloadFile.cpp/
  
#include "winsock2.h"
#include <windows.h>
  
#pragma comment(lib, "Ws2_32.lib")
#pragma comment(linker, "/ENTRY:Main")
  
#define HOST_NAME   "wasm.ru"
#define URL_NAME    "/pub/21/files/lockfileswork/RawRead.rar" 
#define FILE_NAME   "RawRead.rar"
#define HEADER_SIZE 400
  
// Возводим число x в положительную целочисленную степень
#define DEGREE(Val, Deg) if(!Deg) { Val = 1; } else for(int i1=2, i2=Val; i1<=Deg; i1++) { Val *= i2; }                    
 
// Переводим число Str, представленное в виде строки в числовой вид Int
#define STR_TO_INT(Str, Int) for(int l=0, s=10; l<strlen(Str); l++, s=10) { DEGREE(s, (strlen(Str)-1-l)); Int += ((BYTE)Str[l]-0x30)*s; }
   
PCHAR WINAPI HTTPSendReceiveData(PVOID pInData, DWORD dwInDataSize, PCHAR pIpAddress, PDWORD pOutSizeSize)
{ 
    SOCKET      ConnectSocket;
    sockaddr_in ClientService; 
    INT         nReceiveBytes, i, j = 0, nCurr;
    CHAR        szHeader[HEADER_SIZE] = "\0", szVal[10] = "\0";
    PCHAR       pOutData = 0;
  
    if(INVALID_SOCKET == (ConnectSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP))) {
        return 0;
    }
     
    ClientService.sin_family = AF_INET;
    ClientService.sin_port = htons(80);
    ClientService.sin_addr.s_addr = inet_addr(pIpAddress);
    
    if(SOCKET_ERROR == connect(ConnectSocket, (SOCKADDR*)&ClientService, sizeof(ClientService))) {
        closesocket(ConnectSocket);
        return 0;
    }
    
    if(SOCKET_ERROR == send(ConnectSocket, (PCHAR)pInData, dwInDataSize, 0)) {
        closesocket(ConnectSocket);
        return 0;
    }
    
    // Получаем заголовок ответа
    if(SOCKET_ERROR == recv(ConnectSocket, szHeader, HEADER_SIZE, 0)) {
        closesocket(ConnectSocket);
        return 0;
    }
   
    for(i=0; i<HEADER_SIZE; i++) 
    {
        // Получаем размер данных
        if(!memcmp("Content-Length: ", szHeader+i, strlen("Content-Length: ")-1))
        {
            do {
                szVal[j] = szHeader[i+strlen("Content-Length: ")+j]; j++;
            } while(szHeader[i+strlen("Content-Length: ")+j] != '\r');
            
            STR_TO_INT(szVal, *pOutSizeSize);
        }
        // Получаем указатель на начало файла в ответе
        if(!memcmp("\r\n\r\n", szHeader+i, strlen("\r\n\r\n")-1))
        {
            i += strlen("\r\n\r\n");
            break;
        }
    }
    
    if((HEADER_SIZE-1 == i) || !*pOutSizeSize) {
        return 0;
    }
  
    if(!(pOutData = (PCHAR)VirtualAlloc(0, *pOutSizeSize, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE))) {
        return 0;
    }
   
    if(HEADER_SIZE-i >= *pOutSizeSize) {
        memcpy(pOutData, szHeader+i, *pOutSizeSize);
    } else {
        nCurr = HEADER_SIZE-i;
        memcpy(pOutData, szHeader+i, nCurr);
        
        // Получаем оставшиеся данные    
        while(nReceiveBytes = recv(ConnectSocket, pOutData+nCurr, *pOutSizeSize-nCurr, 0))  {
            if(nReceiveBytes == SOCKET_ERROR) {
                closesocket(ConnectSocket);
                return 0;
            }
            nCurr += nReceiveBytes;
        }
    }
   
    closesocket(ConnectSocket);
    
    return pOutData;
}
    
BOOL WINAPI GetIpByHostName(PCHAR pHostName, PCHAR pIp, DWORD dwIpSize)
{
    hostent *pHosten;
    
    if(!(pHosten = gethostbyname(pHostName))) {
        return 0;
    }
    
    if(lstrlen(inet_ntoa(*(in_addr*)*pHosten->h_addr_list)) > dwIpSize) {
        return 0;
    }
    
    lstrcpy(pIp, inet_ntoa(*(in_addr*)*pHosten->h_addr_list));
   
    return 1;
}
   
BOOL WINAPI DownloadFile(PCHAR pFileName, PCHAR pHostName, PCHAR pUrl)
{
    CHAR    szIp[17], szSendData[300];
    PCHAR   pFile = 0;
    HANDLE  hFile;
    DWORD   dwFileSize = 0, dwRetSize;
    
    if(!GetIpByHostName(pHostName, szIp, 17)) {
        return 0;
    }
    
    wsprintf(szSendData, "GET %s HTTP/1.1\r\nHost: %s\r\n\r\n", pUrl, pHostName);
   
    if(!(pFile = HTTPSendReceiveData(szSendData, strlen(szSendData), szIp, &dwFileSize))) {
        return 0;
    }
    
    if(INVALID_HANDLE_VALUE == (hFile = CreateFile(pFileName, GENERIC_WRITE, 0, 0, CREATE_ALWAYS, 0, 0))) {
        VirtualFree(pFile, 0, MEM_RELEASE);
        return 0;
    }
    
    if(!WriteFile(hFile, pFile, dwFileSize, &dwRetSize, 0)) {
        VirtualFree(pFile, 0, MEM_RELEASE);
        CloseHandle(hFile); 
        return 0;
    }
    
    VirtualFree(pFile, 0, MEM_RELEASE);
    CloseHandle(hFile);
    
    return 1;
}
    
VOID WINAPI Main()
{   
    WSAData wsaData;
   
    if(NO_ERROR != WSAStartup(MAKEWORD(2,2), &wsaData)) {
        ExitProcess(0);
    }
   
    if(DownloadFile(FILE_NAME, HOST_NAME, URL_NAME)) {
        MessageBox(0, "DownloadFile Ok", 0, 0);
    } else {
        MessageBox(0, "DownloadFile Error", 0, 0);
    }
   
    ExitProcess(0);
}

Оцени полезность:

15   голосов , оценка 4 из 5
Похожие ответы