Files
fastfetch/src/common/networking.c
T

116 lines
3.2 KiB
C
Raw Normal View History

2022-10-14 16:39:48 +08:00
#ifdef _WIN32
2022-10-12 19:35:23 +08:00
#include <winsock2.h>
#include <ws2tcpip.h>
#include <synchapi.h>
static BOOL WINAPI initWsaData(PINIT_ONCE once, PVOID param, PVOID* context)
{
(void)once;
(void)param;
static WSADATA wsaData;
*context = &wsaData;
return WSAStartup(MAKEWORD(2, 2), &wsaData) == 0;
}
//Types of winsock2 are full of mess. Disable warnings for them and keep clean for posix
#pragma GCC diagnostic ignored "-Wincompatible-pointer-types"
#pragma GCC diagnostic ignored "-Wconversion"
#pragma GCC diagnostic ignored "-Wsign-conversion"
#else
#include <unistd.h>
#include <sys/time.h>
#include <sys/socket.h>
#include <netdb.h>
#define closesocket close
#endif
//Must be included after <winsock2.h>
2022-01-10 20:20:18 +01:00
#include "fastfetch.h"
#include "common/networking.h"
2022-01-10 20:20:18 +01:00
2022-10-12 19:35:23 +08:00
FFSockType ffNetworkingSendHttpRequest(const char* host, const char* path, const char* headers, uint32_t timeout)
2022-01-10 20:20:18 +01:00
{
2022-10-14 16:39:48 +08:00
#ifdef _WIN32
2022-10-12 19:35:23 +08:00
static INIT_ONCE once = INIT_ONCE_STATIC_INIT;
WSADATA* pData;
if(!InitOnceExecuteOnce(&once, initWsaData, NULL, (LPVOID*) &pData))
return INVALID_SOCKET;
#endif
2022-09-28 03:10:33 +08:00
struct addrinfo hints = {
.ai_family = AF_INET,
.ai_socktype = SOCK_STREAM,
};
2022-01-10 20:20:18 +01:00
struct addrinfo* addr;
if(getaddrinfo(host, "80", &hints, &addr) != 0)
2022-10-12 19:35:23 +08:00
return INVALID_SOCKET;
2022-01-10 20:20:18 +01:00
2022-10-12 19:35:23 +08:00
FFSockType sockfd = (FFSockType)socket(addr->ai_family, addr->ai_socktype, addr->ai_protocol);
if(sockfd == INVALID_SOCKET)
2022-01-10 20:20:18 +01:00
{
freeaddrinfo(addr);
2022-10-12 19:35:23 +08:00
return INVALID_SOCKET;
2022-01-10 20:20:18 +01:00
}
if(timeout > 0)
{
struct timeval timev;
timev.tv_sec = 0;
2022-09-04 14:41:00 +02:00
timev.tv_usec = (__typeof__(timev.tv_usec)) (timeout * 1000); //milliseconds to microseconds
2022-09-28 03:10:33 +08:00
setsockopt(sockfd, SOL_SOCKET, SO_RCVTIMEO, &timev, sizeof(timev));
2022-01-10 20:20:18 +01:00
}
2022-09-28 03:10:33 +08:00
if(connect(sockfd, addr->ai_addr, addr->ai_addrlen) == -1)
2022-01-10 20:20:18 +01:00
{
2022-10-12 19:35:23 +08:00
closesocket(sockfd);
2022-01-10 20:20:18 +01:00
freeaddrinfo(addr);
2022-10-12 19:35:23 +08:00
return INVALID_SOCKET;
2022-01-10 20:20:18 +01:00
}
freeaddrinfo(addr);
FFstrbuf command;
ffStrbufInitA(&command, 64);
ffStrbufAppendS(&command, "GET ");
ffStrbufAppendS(&command, path);
ffStrbufAppendS(&command, " HTTP/1.1\nHost: ");
ffStrbufAppendS(&command, host);
2022-09-29 17:05:01 +08:00
ffStrbufAppendS(&command, "\r\n");
ffStrbufAppendS(&command, headers);
ffStrbufAppendS(&command, "\r\n");
2022-01-10 20:20:18 +01:00
2022-09-28 03:10:33 +08:00
if(send(sockfd, command.chars, command.length, 0) == -1)
2022-01-10 20:20:18 +01:00
{
ffStrbufDestroy(&command);
2022-10-12 19:35:23 +08:00
closesocket(sockfd);
return INVALID_SOCKET;
2022-01-10 20:20:18 +01:00
}
2022-09-28 03:10:33 +08:00
ffStrbufDestroy(&command);
return sockfd;
}
2022-01-10 20:20:18 +01:00
2022-10-12 19:35:23 +08:00
bool ffNetworkingRecvHttpResponse(FFSockType sockfd, FFstrbuf* buffer)
2022-09-28 03:10:33 +08:00
{
ssize_t received = recv(sockfd, buffer->chars + buffer->length, ffStrbufGetFree(buffer), 0);
2022-01-10 20:20:18 +01:00
if(received > 0)
{
buffer->length += (uint32_t) received;
buffer->chars[buffer->length] = '\0';
}
2022-10-12 19:35:23 +08:00
closesocket(sockfd);
2022-09-30 17:43:23 +08:00
return ffStrbufStartsWithS(buffer, "HTTP/1.1 200 OK\r\n");
2022-09-28 03:10:33 +08:00
}
2022-09-30 17:43:23 +08:00
bool ffNetworkingGetHttp(const char* host, const char* path, uint32_t timeout, const char* headers, FFstrbuf* buffer)
2022-09-28 03:10:33 +08:00
{
2022-10-12 19:35:23 +08:00
FFSockType sockfd = ffNetworkingSendHttpRequest(host, path, headers, timeout);
if(sockfd != INVALID_SOCKET)
2022-09-30 17:43:23 +08:00
return ffNetworkingRecvHttpResponse(sockfd, buffer);
return false;
2022-01-10 20:20:18 +01:00
}