diff options
author | kartofen <mladenovnasko0@gmail.com> | 2023-01-26 18:34:12 +0200 |
---|---|---|
committer | kartofen <mladenovnasko0@gmail.com> | 2023-01-26 18:34:12 +0200 |
commit | e0a039ad08fc16773cee43e68f92b632a4540bce (patch) | |
tree | ab126ccac9d7b6ba91bfe53e3fbe69df251ebc38 | |
parent | 5e1ae8b33873661b669eda509fcd000f8a964126 (diff) |
automatically knows if i file is text or not
-rw-r--r-- | files/favicon.ico | bin | 1406 -> 0 bytes | |||
-rw-r--r-- | files/favicon.png | bin | 0 -> 7318 bytes | |||
-rw-r--r-- | files/index.html | 1 | ||||
-rw-r--r-- | src/main.c | 101 |
4 files changed, 79 insertions, 23 deletions
diff --git a/files/favicon.ico b/files/favicon.ico Binary files differdeleted file mode 100644 index 91a517f..0000000 --- a/files/favicon.ico +++ /dev/null diff --git a/files/favicon.png b/files/favicon.png Binary files differnew file mode 100644 index 0000000..268246c --- /dev/null +++ b/files/favicon.png diff --git a/files/index.html b/files/index.html index 3a1c80c..b94ee21 100644 --- a/files/index.html +++ b/files/index.html @@ -2,6 +2,7 @@ <html> <head> <title>Test</title> + <link rel="icon" href="/favicon.png"> </head> <body> <h1>Server</h1> @@ -9,21 +9,85 @@ #include "server.h" #define BUF_CAP 80000 +#define COMMON_CAP 1024 #define PORT "8079" +#define RM_LF(str) do { \ + signed long len = strlen(str)-1; \ + if(len >= 0 && str[len] == '\n') str[len] = '\0'; \ + } while(0) + +#define _SEND_BUF_ADD(str) do { \ + memcpy(&send_buf[send_buf_sz], str, strlen(str)); \ + send_buf_sz += strlen(str); \ + } while(0) +#define _SEND_BUF_ADD_LINE(str) do { \ + _SEND_BUF_ADD(str); \ + _SEND_BUF_ADD("\r\n"); \ + } while(0) + #define SEND_BUF_ADD(str) do { \ memcpy(&send_buf[*send_buf_sz], str, strlen(str)); \ *send_buf_sz += strlen(str); \ } while(0) - #define SEND_BUF_ADD_LINE(str) do { \ SEND_BUF_ADD(str); \ SEND_BUF_ADD("\r\n"); \ } while(0) -static int try_file(char *req_path, FILE **fp) +#define LOAD_FILE() do { \ + if(is_binary) { \ + fseek(fp, 0, SEEK_END); \ + size_t file_sz = ftell(fp); \ + rewind(fp); \ + \ + fread(&send_buf[*send_buf_sz], sizeof(char), file_sz, fp); \ + *send_buf_sz += file_sz; \ + } else { \ + char line[BUF_CAP]; \ + while(fgets(line, sizeof(line), fp) != NULL) \ + { \ + RM_LF(line); \ + SEND_BUF_ADD_LINE(line); \ + } \ + } \ + } while(0) + +static int get_content_type(char *file_path, char *content_type) { - char file_path[1024]; + char cmd[COMMON_CAP + 64]; + sprintf(cmd, "/usr/bin/file -ib %s", file_path); + + FILE *fp = popen(cmd, "r"); + if(!fp) { + err("popen: cmd %s: %s", cmd, strerror(errno)); + return 1; + } + + if(fgets(content_type, COMMON_CAP, fp) == NULL) { + err("get_mime_type: no output from fgets"); + return 1; + } + + pclose(fp); + RM_LF(content_type); + + char ct_cpy[COMMON_CAP]; + strcpy(ct_cpy, content_type); + strtok(ct_cpy, "="); + + // the only thing after the '=' should be the either binary or something else (text) + char *charset = strtok(NULL, "="); + if(charset == NULL || strcmp(charset, "binary") != 0) { + return 0; + } + + return -1; +} + +static int try_file(char *req_path, FILE **fp, char *content_type) +{ + char file_path[COMMON_CAP]; sprintf(file_path, "%s%s", FILES, (strlen(req_path) == 1) ? "/index.html" : req_path); @@ -33,43 +97,33 @@ static int try_file(char *req_path, FILE **fp) return 1; } info("fopen: file %s was opened", file_path); - return 0; + + return get_content_type(file_path, content_type); } static int on_get(char *send_buf, ssize_t *send_buf_sz, char *req_path) { - SEND_BUF_ADD("HTTP/1.1 "); + char content_type[COMMON_CAP]; + int is_binary; // 0 - no; -1 - yes; 1 - error FILE *fp; - if(try_file(req_path, &fp) != 0) { + if((is_binary = try_file(req_path, &fp, content_type)) == 1) { if(errno == 2) { // 2 is 'No such file or directory' SEND_BUF_ADD_LINE("404"); - if(try_file("/404.html", &fp) != 0) return 1; + if((is_binary = try_file("/404.html", &fp, content_type)) != 0) return 1; } else { SEND_BUF_ADD_LINE("500"); - if(try_file("/505.html", &fp) != 0) return 1; + if((is_binary = try_file("/500.html", &fp, content_type)) != 0) return 1; } } else { SEND_BUF_ADD_LINE("200"); } SEND_BUF_ADD_LINE("Server: potato"); - // SEND_BUF_ADD_LINE("Content-Type: image/x-icon"); + SEND_BUF_ADD("Content-Type: "); + SEND_BUF_ADD_LINE(content_type); SEND_BUF_ADD("\r\n"); - - // fseek(fp, 0, SEEK_END); - // size_t file_sz = ftell(fp); - // rewind(fp); - - // fread(&send_buf[*send_buf_sz], sizeof(char), file_sz, fp); - // *send_buf_sz += file_sz; - - char line[BUF_CAP]; - while(fgets(line, sizeof(line), fp) != NULL) - { - if(line[strlen(line)-1] == '\n') line[strlen(line)-1] = '\0'; - SEND_BUF_ADD_LINE(line); - } + LOAD_FILE(); fclose(fp); return 0; @@ -91,6 +145,7 @@ static int handle_connection(sock_t *conn) char send_buf[BUF_CAP]; ssize_t send_buf_sz = 0; + _SEND_BUF_ADD("HTTP/1.1 "); char recv_buf_cpy[BUF_CAP]; memcpy(recv_buf_cpy, recv_buf, recv_buf_len); |