#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <unistd.h>
#include <netdb.h>
#define SERVER_IP "192.168.85.207"
#define PORT 8080
#define BUFFER_SIZE 1024
/*
* Generate an HTTP GET request for a static snapshot.
* This function creates a properly formatted HTTP GET request string
* to retrieve a static snapshot from an mjpg - streamer server.
* Return: A pointer to the generated request string.
*/
char* generate_get_request() {
char* request = (char*)malloc(1024);
if (request == NULL) {
perror("malloc error");
exit(EXIT_FAILURE);
}
sprintf(request, "GET /?action=snapshot HTTP/1.1\r\n"
"Host: %s:%d\r\n"
"User - Agent: Mozilla/5.0 (X11; Linux x86_64; rv:78.0) Gecko/20100101 Firefox/78.0\r\n"
"Accept: image/jpeg\r\n"
"Connection: close\r\n\r\n", SERVER_IP, PORT);
return request;
}
/*
* Read data from the server and save it as a file.
* This function handles receiving data from the server and writing it to a file.
* It first skips the HTTP header information and then saves the image data.
* Parameters:
* - sockfd: The socket file descriptor connected to the server.
*/
void save_image_from_server(int sockfd) {
FILE *fp;
char buffer[BUFFER_SIZE];
size_t bytes_read;
/* Open a file to write the image data */
fp = fopen("received_image.jpg", "wb");
if (fp == NULL) {
perror("Error opening file");
close(sockfd);
exit(EXIT_FAILURE);
}
/* Skip the HTTP header information */
char* http_header_end;
do {
bytes_read = recv(sockfd, buffer, BUFFER_SIZE, 0);
if (bytes_read <= 0) {
perror("Error receiving HTTP header");
fclose(fp);
close(sockfd);
exit(EXIT_FAILURE);
}
printf("Received bytes in header loop: %zu\n", bytes_read);
http_header_end = strstr(buffer, "\r\n\r\n");
} while (http_header_end == NULL);
/* Start writing the image data (skip the HTTP header) */
fwrite(http_header_end + 4, 1, bytes_read - (http_header_end + 4 - buffer), fp);
/* Continue receiving and saving the remaining image data */
while ((bytes_read = recv(sockfd, buffer, BUFFER_SIZE, 0)) > 0) {
printf("Received bytes of image data: %zu\n", bytes_read);
fwrite(buffer, 1, bytes_read, fp);
}
if (bytes_read < 0) {
perror("Error receiving image data");
}
fclose(fp);
}
int main() {
int sockfd;
struct sockaddr_in server_addr;
char* request;
/* Create a socket */
sockfd = socket(AF_INET, SOCK_STREAM, 0);
if (sockfd < 0) {
perror("Error creating socket");
exit(EXIT_FAILURE);
}
printf("Socket created.\n");
/* Set up the server address structure */
server_addr.sin_family = AF_INET;
server_addr.sin_port = htons(PORT);
server_addr.sin_addr.s_addr = inet_addr(SERVER_IP);
/* Connect to the server */
if (connect(sockfd, (struct sockaddr *)&server_addr, sizeof(server_addr)) < 0) {
perror("Error connecting to server");
close(sockfd);
exit(EXIT_FAILURE);
}
printf("Connected to the server.\n");
/* Generate an HTTP GET request for a static snapshot */
request = generate_get_request();
/* Send the request */
if (send(sockfd, request, strlen(request), 0) < 0) {
perror("Error sending request");
free(request);
close(sockfd);
exit(EXIT_FAILURE);
}
free(request);
printf("Request sent.\n");
/* Get and save the image from the server */
save_image_from_server(sockfd);
/* Close the socket connection */
close(sockfd);
printf("Socket closed.\n");
return 0;
}