Skip to content

Instantly share code, notes, and snippets.

@asutoshpalai
Created August 19, 2016 19:33
Show Gist options
  • Save asutoshpalai/46a45cb7d7d3202877a361a33f3b0db3 to your computer and use it in GitHub Desktop.
Save asutoshpalai/46a45cb7d7d3202877a361a33f3b0db3 to your computer and use it in GitHub Desktop.
#include <stdio.h>
#include <fcntl.h>
#include <string.h>
#include <stdlib.h>
#include <stdbool.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netdb.h>
#include <unistd.h>
#include <sys/types.h>
char *get(char *, int);
void open_file(char *dest);
int main() {
char *url = NULL;
int len;
getline(&url, &len, stdin);
char *tmp = strchr(url, '\n');
if(tmp != NULL)
*tmp = '\0';
char *dest = get(url, len);
if(dest != NULL) {
open_file(dest);
}
free(dest);
}
char *fetch(char *host, int port, char* loc);
char *get(char * url, int len) {
int port = 80;
char *host, *location;
char *proto_excluded = strstr(url, "//");
if(proto_excluded != NULL)
proto_excluded += 2;
else
proto_excluded = url;
location = strchr(proto_excluded, '/');
int host_length;
if(location == NULL)
host_length = strlen(proto_excluded);
else
host_length = location - proto_excluded;
host = malloc(sizeof(char) * (host_length + 1));
strncpy(host, proto_excluded, host_length);
host[host_length] = '\0';
char *ptr = strchr(host, ':');
if(ptr != NULL) {
port = atoi(ptr + 1);
*ptr = '\0';
host_length -= strlen(ptr + 1);
}
char *dest;
if(location == NULL) {
dest = fetch(host, port, "/");
}
else {
dest = fetch(host, port, location);
}
free(host);
return dest;
}
void open_file(char *dest) {
pid_t child = fork();
if(child < 0) {
perror("Error forking");
}
else if(child == 0) {
int devNull = open("/dev/null", O_WRONLY);
dup2(devNull, STDOUT_FILENO);
dup2(devNull, STDERR_FILENO);
close(devNull);
execl("/usr/bin/xdg-open", "xdg-open", dest, (char *)0);
exit(0);
}
else {
wait();
}
}
char *fetch(char *host, int port, char* loc){
printf("host: %s, port : %d, loc: %s\n", host, port, loc);
char tmpname[] = "/tmp/text_file";
char *fileName = malloc(sizeof(char) * sizeof(tmpname));
strcpy(fileName, tmpname);
int sockfd = 0;
const int buffSize = 1024;
char recvBuff[buffSize], sendBuff[buffSize];
struct sockaddr_in serveraddr;
struct hostent *server;
sockfd = socket(AF_INET, SOCK_STREAM, 0);
if(sockfd < 0) {
perror("Failed to create socket\n");
return NULL;
}
server = gethostbyname(host);
if (server == NULL) {
fprintf(stderr,"ERROR, no such host as %s\n", host);
return NULL;
}
bzero((char *) &serveraddr, sizeof(serveraddr));
serveraddr.sin_family = AF_INET;
bcopy((char *)server->h_addr,
(char *)&serveraddr.sin_addr.s_addr, server->h_length);
serveraddr.sin_port = htons(port);
if (connect(sockfd, (struct sockaddr*)&serveraddr, sizeof(serveraddr)) < 0) {
perror("Failed to connect to server\n");
return NULL;
}
sprintf(sendBuff, "GET %s HTTP/1.0\r\nHost: %s\r\n\r\n", loc, host);
int n = write(sockfd, sendBuff, strlen(sendBuff));
if(n <= 0) {
perror("Failed to write to socket\n");
return NULL;
}
FILE *fp = fopen(fileName, "w+");
bool header_ended = false;
char *ptr;
while((n = read(sockfd, recvBuff, buffSize)) > 0) {
if(header_ended == false && (ptr = strstr(recvBuff, "\r\n\r\n")) != NULL) {
ptr = ptr + 4;
fwrite(ptr, sizeof(char), n - (ptr - recvBuff) + 1, fp);
header_ended = true;
}
else if(header_ended == true) {
fwrite(recvBuff, sizeof(char), n, fp);
}
}
fclose(fp);
return fileName;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment