diff options
author | Rodrigo Arias Mallo <rodarima@gmail.com> | 2023-12-12 21:27:08 +0100 |
---|---|---|
committer | Rodrigo Arias Mallo <rodrigo.arias@bsc.es> | 2023-12-21 01:05:58 +0100 |
commit | 1da1260af72b20126176e2b8f73f7b7fd5952ce1 (patch) | |
tree | 0fcdb276d30814ce4075f7cc205e357b2b7c1be5 /test/cookies.c | |
parent | 78ad5bfe9644d1217f9d9ad0bf2fcdc388551113 (diff) |
Split tests into unit and dw (graphical)
Graphical tests for the dw (Dillo Widget) are moved to test/dw, while
unit tests are placed into test/unit.
All tests are compiled with "make check" but only the tests that can run
without intervention and without a graphic display are executed.
Diffstat (limited to 'test/cookies.c')
-rw-r--r-- | test/cookies.c | 1164 |
1 files changed, 0 insertions, 1164 deletions
diff --git a/test/cookies.c b/test/cookies.c deleted file mode 100644 index eaa0f59d..00000000 --- a/test/cookies.c +++ /dev/null @@ -1,1164 +0,0 @@ -/* - * Dillo cookies test - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 3 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -/* - * This has a big blob of the current src/IO/dpi.c in it. - * I hope there's a better way. - */ - -#include <stdlib.h> /* malloc, etc. */ -#include <unistd.h> /* read, etc. */ -#include <stdio.h> -#include <stdarg.h> /* va_list */ -#include <string.h> /* strchr */ -#include <errno.h> -#include <ctype.h> -#include <time.h> -/* net */ -#include <sys/types.h> -#include <sys/socket.h> -#include <arpa/inet.h> -#include <netinet/in.h> - - -#define _MSG(...) - -#define MSG_INNARDS(prefix, ...) \ - D_STMT_START { \ - printf(prefix __VA_ARGS__); \ - fflush (stdout); \ - } D_STMT_END - -#define MSG(...) MSG_INNARDS("", __VA_ARGS__) -#define MSG_WARN(...) MSG_INNARDS("** WARNING **: ", __VA_ARGS__) -#define MSG_ERR(...) MSG_INNARDS("** ERROR **: ", __VA_ARGS__) - - -#include "../dlib/dlib.h" -#include "../dpip/dpip.h" - -static uint_t failed = 0; -static uint_t passed = 0; - -static char SharedKey[32]; - -/* - * Read all the available data from a filedescriptor. - * This is intended for short answers, i.e. when we know the server - * will write it all before being preempted. For answers that may come - * as an stream with delays, non-blocking is better. - * Return value: read data, or NULL on error and no data. - */ -static char *Dpi_blocking_read(int fd) -{ - int st; - const int buf_sz = 8*1024; - char buf[buf_sz], *msg = NULL; - Dstr *dstr = dStr_sized_new(buf_sz); - - do { - st = read(fd, buf, buf_sz); - if (st < 0) { - if (errno == EINTR) { - continue; - } else { - MSG_ERR("[Dpi_blocking_read] %s\n", dStrerror(errno)); - break; - } - } else if (st > 0) { - dStr_append_l(dstr, buf, st); - } - } while (st == buf_sz); - - msg = (dstr->len > 0) ? dstr->str : NULL; - dStr_free(dstr, (dstr->len > 0) ? FALSE : TRUE); - return msg; -} - -static void Dpi_close_fd(int fd) -{ - int st; - - dReturn_if (fd < 0); - do - st = close(fd); - while (st < 0 && errno == EINTR); -} - -static int Dpi_make_socket_fd() -{ - int fd, ret = -1; - - if ((fd = socket(AF_INET, SOCK_STREAM, 0)) != -1) { - ret = fd; - } - return ret; -} - -/* - * Read dpid's communication keys from its saved file. - * Return value: 1 on success, -1 on error. - */ -static int Dpi_read_comm_keys(int *port) -{ - FILE *In; - char *fname, *rcline = NULL, *tail; - int i, ret = -1; - - fname = dStrconcat(dGethomedir(), "/.dillo/dpid_comm_keys", NULL); - if ((In = fopen(fname, "r")) == NULL) { - MSG_ERR("[Dpi_read_comm_keys] %s\n", dStrerror(errno)); - } else if ((rcline = dGetline(In)) == NULL) { - MSG_ERR("[Dpi_read_comm_keys] empty file: %s\n", fname); - } else { - *port = strtol(rcline, &tail, 10); - for (i = 0; *tail && isxdigit(tail[i+1]); ++i) - SharedKey[i] = tail[i+1]; - SharedKey[i] = 0; - ret = 1; - } - if (In) - fclose(In); - dFree(rcline); - dFree(fname); - - return ret; -} - -static int Dpi_check_dpid_ids() -{ - struct sockaddr_in sin; - const socklen_t sin_sz = sizeof(sin); - int sock_fd, dpid_port, ret = -1; - - /* socket connection test */ - memset(&sin, 0, sizeof(sin)); - sin.sin_family = AF_INET; - sin.sin_addr.s_addr = htonl(INADDR_LOOPBACK); - - if (Dpi_read_comm_keys(&dpid_port) != -1) { - sin.sin_port = htons(dpid_port); - if ((sock_fd = Dpi_make_socket_fd()) == -1) { - MSG("Dpi_check_dpid_ids: sock_fd=%d %s\n", sock_fd, dStrerror(errno)); - } else if (connect(sock_fd, (struct sockaddr *)&sin, sin_sz) == -1) { - MSG("Dpi_check_dpid_ids: %s\n", dStrerror(errno)); - } else { - Dpi_close_fd(sock_fd); - ret = 1; - } - } - return ret; -} - -static int Dpi_blocking_write(int fd, const char *msg, int msg_len) -{ - int st, sent = 0; - - while (sent < msg_len) { - st = write(fd, msg + sent, msg_len - sent); - if (st < 0) { - if (errno == EINTR) { - continue; - } else { - MSG_ERR("[Dpi_blocking_write] %s\n", dStrerror(errno)); - break; - } - } - sent += st; - } - - return (sent == msg_len) ? 1 : -1; -} - -/* - * Start dpid. - * Return: 0 starting now, 1 Error. - */ -static int Dpi_start_dpid(void) -{ - pid_t pid; - int st_pipe[2], ret = 1; - char *answer; - - /* create a pipe to track our child's status */ - if (pipe(st_pipe)) - return 1; - - pid = fork(); - if (pid == 0) { - /* This is the child process. Execute the command. */ - char *path1 = dStrconcat(dGethomedir(), "/.dillo/dpid", NULL); - Dpi_close_fd(st_pipe[0]); - if (execl(path1, "dpid", (char*)NULL) == -1) { - dFree(path1); - if (execlp("dpid", "dpid", (char*)NULL) == -1) { - MSG("Dpi_start_dpid (child): %s\n", dStrerror(errno)); - if (Dpi_blocking_write(st_pipe[1], "ERROR", 5) == -1) { - MSG("Dpi_start_dpid (child): can't write to pipe.\n"); - } - Dpi_close_fd(st_pipe[1]); - _exit (EXIT_FAILURE); - } - } - } else if (pid < 0) { - /* The fork failed. Report failure. */ - MSG("Dpi_start_dpid: %s\n", dStrerror(errno)); - /* close the unused pipe */ - Dpi_close_fd(st_pipe[0]); - Dpi_close_fd(st_pipe[1]); - - } else { - /* This is the parent process, check our child status... */ - Dpi_close_fd(st_pipe[1]); - if ((answer = Dpi_blocking_read(st_pipe[0])) != NULL) { - MSG("Dpi_start_dpid: can't start dpid\n"); - dFree(answer); - } else { - ret = 0; - } - Dpi_close_fd(st_pipe[0]); - } - - return ret; -} - -/* - * Confirm that the dpid is running. If not, start it. - * Return: 0 running OK, 1 starting (EAGAIN), 2 Error. - */ -static int Dpi_check_dpid(int num_tries) -{ - static int starting = 0; - int check_st = 1, ret = 2; - - check_st = Dpi_check_dpid_ids(); - _MSG("Dpi_check_dpid: check_st=%d\n", check_st); - - if (check_st == 1) { - /* connection test with dpi server passed */ - starting = 0; - ret = 0; - } else { - if (!starting) { - /* start dpid */ - if (Dpi_start_dpid() == 0) { - starting = 1; - ret = 1; - } - } else if (++starting < num_tries) { - /* starting */ - ret = 1; - } else { - /* we waited too much, report an error... */ - starting = 0; - } - } - - _MSG("Dpi_check_dpid:: %s\n", - (ret == 0) ? "OK" : (ret == 1 ? "EAGAIN" : "ERROR")); - return ret; -} - - -static int Dpi_blocking_start_dpid(void) -{ - int cst, try = 0, - n_tries = 12; /* 3 seconds */ - - /* test the dpid, and wait a bit for it to start if necessary */ - while ((cst = Dpi_check_dpid(n_tries)) == 1) { - MSG("Dpi_blocking_start_dpid: try %d\n", ++try); - usleep(250000); /* 1/4 sec */ - } - return cst; -} - - -/* - * Return the dpi server's port number, or -1 on error. - * (A query is sent to dpid and then its answer parsed) - * note: as the available servers and/or the dpi socket directory can - * change at any time, we'll ask each time. If someday we find - * that connecting each time significantly degrades performance, - * an optimized approach can be tried. - */ -static int Dpi_get_server_port(const char *server_name) -{ - int sock_fd = -1, dpi_port = -1; - int dpid_port, ok = 0; - struct sockaddr_in sin; - char *cmd, *request, *rply = NULL, *port_str; - socklen_t sin_sz; - - dReturn_val_if_fail (server_name != NULL, dpi_port); - _MSG("Dpi_get_server_port:: server_name = [%s]\n", server_name); - - /* Read dpid's port from saved file */ - if (Dpi_read_comm_keys(&dpid_port) != -1) { - ok = 1; - } - if (ok) { - /* Connect a socket with dpid */ - ok = 0; - sin_sz = sizeof(sin); - memset(&sin, 0, sizeof(sin)); - sin.sin_family = AF_INET; - sin.sin_addr.s_addr = htonl(INADDR_LOOPBACK); - sin.sin_port = htons(dpid_port); - if ((sock_fd = Dpi_make_socket_fd()) == -1 || - connect(sock_fd, (struct sockaddr *)&sin, sin_sz) == -1) { - MSG("Dpi_get_server_port: %s\n", dStrerror(errno)); - } else { - ok = 1; - } - } - if (ok) { - /* ask dpid to check the dpi and send its port number back */ - ok = 0; - request = a_Dpip_build_cmd("cmd=%s msg=%s", "check_server", server_name); - _MSG("[%s]\n", request); - - if (Dpi_blocking_write(sock_fd, request, strlen(request)) == -1) { - MSG("Dpi_get_server_port: %s\n", dStrerror(errno)); - } else { - ok = 1; - } - dFree(request); - } - if (ok) { - /* Get the reply */ - ok = 0; - if ((rply = Dpi_blocking_read(sock_fd)) == NULL) { - MSG("Dpi_get_server_port: can't read server port from dpid.\n"); - } else { - ok = 1; - } - } - if (ok) { - /* Parse reply */ - ok = 0; - cmd = a_Dpip_get_attr(rply, "cmd"); - if (strcmp(cmd, "send_data") == 0) { - port_str = a_Dpip_get_attr(rply, "msg"); - _MSG("Dpi_get_server_port: rply=%s\n", rply); - _MSG("Dpi_get_server_port: port_str=%s\n", port_str); - dpi_port = strtol(port_str, NULL, 10); - dFree(port_str); - ok = 1; - } - dFree(cmd); - } - dFree(rply); - Dpi_close_fd(sock_fd); - - return ok ? dpi_port : -1; -} - - -static int Dpi_connect_socket(const char *server_name) -{ - struct sockaddr_in sin; - int sock_fd, dpi_port, ret = -1; - char *cmd = NULL; - - /* Query dpid for the port number for this server */ - if ((dpi_port = Dpi_get_server_port(server_name)) == -1) { - _MSG("Dpi_connect_socket:: can't get port number for %s\n", server_name); - return -1; - } - _MSG("Dpi_connect_socket: server=%s port=%d\n", server_name, dpi_port); - - /* connect with this server's socket */ - memset(&sin, 0, sizeof(sin)); - sin.sin_family = AF_INET; - sin.sin_addr.s_addr = htonl(INADDR_LOOPBACK); - sin.sin_port = htons(dpi_port); - - if ((sock_fd = Dpi_make_socket_fd()) == -1) { - perror("[dpi::socket]"); - } else if (connect(sock_fd, (void*)&sin, sizeof(sin)) == -1) { - MSG("[dpi::connect] errno:%d %s\n", errno, dStrerror(errno)); - - /* send authentication Key (the server closes sock_fd on auth error) */ - } else if (!(cmd = a_Dpip_build_cmd("cmd=%s msg=%s", "auth", SharedKey))) { - MSG_ERR("[Dpi_connect_socket] Can't make auth message.\n"); - } else if (Dpi_blocking_write(sock_fd, cmd, strlen(cmd)) == -1) { - MSG_ERR("[Dpi_connect_socket] Can't send auth message.\n"); - } else { - ret = sock_fd; - } - dFree(cmd); - if (sock_fd != -1 && ret == -1) /* can't send cmd? */ - Dpi_close_fd(sock_fd); - - return ret; -} - - -char *a_Dpi_send_blocking_cmd(const char *server_name, const char *cmd) -{ - int cst, sock_fd; - char *ret = NULL; - - /* test the dpid, and wait a bit for it to start if necessary */ - if ((cst = Dpi_blocking_start_dpid()) != 0) { - return ret; - } - - if ((sock_fd = Dpi_connect_socket(server_name)) == -1) { - MSG_ERR("[a_Dpi_send_blocking_cmd] Can't connect to server.\n"); - } else if (Dpi_blocking_write(sock_fd, cmd, strlen(cmd)) == -1) { - MSG_ERR("[a_Dpi_send_blocking_cmd] Can't send message.\n"); - } else if ((ret = Dpi_blocking_read(sock_fd)) == NULL) { - MSG_ERR("[a_Dpi_send_blocking_cmd] Can't read message.\n"); - } - Dpi_close_fd(sock_fd); - - return ret; -} - - - -void a_Cookies_set(const char *cookie, const char *host, const char *path, - const char *date) -{ - char *cmd, *dpip_tag; - - if (date) - cmd = a_Dpip_build_cmd("cmd=%s cookie=%s host=%s path=%s date=%s", - "set_cookie", cookie, - host, path, date); - else - cmd = a_Dpip_build_cmd("cmd=%s cookie=%s host=%s path=%s", - "set_cookie", cookie, - host, path); - - dpip_tag = a_Dpi_send_blocking_cmd("cookies", cmd); - _MSG("a_Cookies_set: dpip_tag = {%s}\n", dpip_tag); - dFree(dpip_tag); - dFree(cmd); -} - - -char *a_Cookies_get_query(const char *scheme, const char *host, - const char *path) -{ - char *cmd, *dpip_tag, *query; - - cmd = a_Dpip_build_cmd("cmd=%s scheme=%s host=%s path=%s", - "get_cookie", scheme, - host, path); - - /* Get the answer from cookies.dpi */ - _MSG("cookies.c: a_Dpi_send_blocking_cmd cmd = {%s}\n", cmd); - dpip_tag = a_Dpi_send_blocking_cmd("cookies", cmd); - _MSG("cookies.c: after a_Dpi_send_blocking_cmd resp={%s}\n", dpip_tag); - dFree(cmd); - - if (dpip_tag != NULL) { - query = a_Dpip_get_attr(dpip_tag, "cookie"); - dFree(dpip_tag); - } else { - query = dStrdup(""); - } - - return query; -} - -static void expect(int lineno, const char *exp_reply, - const char *scheme, const char *host, const char *path) -{ - char *reply = a_Cookies_get_query(scheme, host, path); - - if (strcmp(reply, exp_reply)) { - MSG("line %d: EXPECTED: %s GOT: %s\n", lineno, exp_reply, reply); - failed++; - } else { - passed++; - } -} - -static void toomany() -{ - a_Cookies_set("1=1", "toomany.com", "/", NULL); - a_Cookies_set("2=1", "toomany.com", "/", NULL); - a_Cookies_set("3=1", "toomany.com", "/", NULL); - a_Cookies_set("4=1", "toomany.com", "/", NULL); - a_Cookies_set("5=1", "toomany.com", "/", NULL); - a_Cookies_set("6=1", "toomany.com", "/", NULL); - a_Cookies_set("7=1", "toomany.com", "/path/", NULL); - a_Cookies_set("8=1", "toomany.com", "/", NULL); - a_Cookies_set("9=1", "toomany.com", "/", NULL); - a_Cookies_set("10=1", "toomany.com", "/", NULL); - a_Cookies_set("11=1", "toomany.com", "/", NULL); - a_Cookies_set("12=1", "toomany.com", "/", NULL); - a_Cookies_set("13=1", "toomany.com", "/", NULL); - a_Cookies_set("14=1", "toomany.com", "/", NULL); - a_Cookies_set("15=1", "toomany.com", "/", NULL); - a_Cookies_set("16=1", "toomany.com", "/", NULL); - a_Cookies_set("17=1", "toomany.com", "/", NULL); - a_Cookies_set("18=1", "toomany.com", "/", NULL); - a_Cookies_set("19=1", "toomany.com", "/", NULL); - a_Cookies_set("20=1", "toomany.com", "/", NULL); - a_Cookies_set("21=1", "toomany.com", "/", NULL); - /* 1 was oldest and discarded */ - expect(__LINE__, "Cookie: 7=1; 2=1; 3=1; 4=1; 5=1; 6=1; 8=1; 9=1; 10=1; " - "11=1; 12=1; 13=1; 14=1; 15=1; 16=1; 17=1; 18=1; 19=1; " - "20=1; 21=1\r\n", "http", "toomany.com", "/path/"); - sleep(1); - /* touch all of them except #7 (path matching) */ - expect(__LINE__, "Cookie: 2=1; 3=1; 4=1; 5=1; 6=1; 8=1; 9=1; 10=1; " - "11=1; 12=1; 13=1; 14=1; 15=1; 16=1; 17=1; 18=1; 19=1; " - "20=1; 21=1\r\n", "http", "toomany.com", "/"); - a_Cookies_set("22=1", "toomany.com", "/", NULL); - /* 7 was oldest and discarded */ - expect(__LINE__, "Cookie: 2=1; 3=1; 4=1; 5=1; 6=1; 8=1; 9=1; 10=1; " - "11=1; 12=1; 13=1; 14=1; 15=1; 16=1; 17=1; 18=1; 19=1; " - "20=1; 21=1; 22=1\r\n", "http", "toomany.com", "/path/"); -} - -static void maxage() -{ - time_t t = time(NULL)+1000; - char *server_date = dStrdup(ctime(&t)); - - a_Cookies_set("name=val; max-age=0", "maxage0.com", "/", NULL); - expect(__LINE__, "", "http", "maxage0.com", "/"); - - a_Cookies_set("name=val; max-age=-0", "maxage-0.com", "/", NULL); - expect(__LINE__, "", "http", "maxage-0.com", "/"); - - a_Cookies_set("name=val; max-age=100", "maxage100.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "maxage100.com", "/"); - - a_Cookies_set("name=val; max-age=-100", "maxage-100.com", "/", NULL); - expect(__LINE__, "", "http", "maxage-100.com", "/"); - - a_Cookies_set("name=val; max-age=2000000000", "maxage2bil.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "maxage2bil.com", "/"); - - a_Cookies_set("name=val; max-age=3000000000", "maxage3bil.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "maxage3bil.com", "/"); - - a_Cookies_set("name=val; max-age=7000000000", "maxage7bil.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "maxage7bil.com", "/"); - - a_Cookies_set("name=val; max-age=-2000000000", "maxage-2bil.com", "/",NULL); - expect(__LINE__, "", "http", "maxage-2bil.com", "/"); - - a_Cookies_set("name=val; max-age=-3000000000", "maxage-3bil.com", "/",NULL); - expect(__LINE__, "", "http", "maxage-3bil.com", "/"); - - a_Cookies_set("name=val; max-age=-7000000000", "maxage-7bil.com", "/",NULL); - expect(__LINE__, "", "http", "maxage-7bil.com", "/"); - - /* just having a server date shouldn't matter */ - - a_Cookies_set("name=val; max-age=0", "maxage0s.com", "/", server_date); - expect(__LINE__, "", "http", "maxage0s.com", "/"); - - a_Cookies_set("name=val; max-age=100", "maxage100s.com", "/", server_date); - expect(__LINE__, "Cookie: name=val\r\n", "http", "maxage100s.com", "/"); - - a_Cookies_set("name=val; max-age=-100", "maxage-100s.com", "/",server_date); - expect(__LINE__, "", "http", "maxage-100s.com", "/"); - - /* MAX-AGE and EXPIRES */ - a_Cookies_set("name=val; max-age=90; expires=Wed Jan 20 01:26:32 2010", - "maxagelater.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "maxagelater.com", "/"); - - a_Cookies_set("name=val; max-age=90; expires=Wed Jan 20 01:26:32 2010", - "maxagelaters.com", "/", server_date); - expect(__LINE__, "Cookie: name=val\r\n", "http", "maxagelaters.com", "/"); - - dFree(server_date); -} - -static void expires_server_ahead() -{ - char *string; - time_t t = time(NULL)+1000; - char *server_date = dStrdup(ctime(&t)); - time_t expt = t + 1000; - char *exp_date = dStrdup(ctime(&expt)); - - string = dStrconcat("name=val; expires=", exp_date, NULL); - a_Cookies_set(string, "e2000s1000.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "e2000s1000.com", "/"); - - a_Cookies_set(string, "e2000s1000s.com", "/", server_date); - expect(__LINE__, "Cookie: name=val\r\n", "http", "e2000s1000s.com", "/"); - - expt = t - 500; /* past for the server, future for us */ - dFree(exp_date); - exp_date = dStrdup(ctime(&expt)); - - string = dStrconcat("name=val; expires=", exp_date, NULL); - a_Cookies_set(string, "e500s1000.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "e500s1000.com", "/"); - - a_Cookies_set(string, "e500s1000s.com", "/", server_date); - expect(__LINE__, "", "http", "e500s1000s.com", "/"); - - expt = t; /* expire at future-for-us server date */ - dFree(exp_date); - exp_date = dStrdup(ctime(&expt)); - - string = dStrconcat("name=val; expires=", exp_date, NULL); - a_Cookies_set(string, "e1000s1000.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "e1000s1000.com", "/"); - - a_Cookies_set(string, "e1000s1000s.com", "/", server_date); - expect(__LINE__, "", "http", "e1000s1000s.com", "/"); - - expt = time(NULL); /* now */ - dFree(exp_date); - exp_date = dStrdup(ctime(&expt)); - - string = dStrconcat("name=val; expires=", exp_date, NULL); - a_Cookies_set(string, "e0s1000.com", "/", NULL); - expect(__LINE__, "", "http", "e0s1000.com", "/"); - - a_Cookies_set(string, "e0s1000s.com", "/", server_date); - expect(__LINE__, "", "http", "e0s1000s.com", "/"); - - dFree(exp_date); - dFree(server_date); -} - -static void expires_server_behind() -{ - char *string; - time_t t = time(NULL)-1000; - char *server_date = dStrdup(ctime(&t)); - - time_t expt = t + 1000; - char *exp_date = dStrdup(ctime(&expt)); - - string = dStrconcat("name=val; expires=", exp_date, NULL); - a_Cookies_set(string, "e0s-1000.com", "/", NULL); - expect(__LINE__, "", "http", "e0s-1000.com", "/"); - - a_Cookies_set(string, "e0s-1000s.com", "/", server_date); - expect(__LINE__, "Cookie: name=val\r\n", "http", "e0s-1000s.com","/"); - - expt = t + 500; /* future for the server, past for us */ - dFree(exp_date); - exp_date = dStrdup(ctime(&expt)); - - string = dStrconcat("name=val; expires=", exp_date, NULL); - a_Cookies_set(string, "e-500s-1000.com", "/", NULL); - expect(__LINE__, "", "http", "e-500s-1000.com", "/"); - - a_Cookies_set(string, "e-500s-1000s.com", "/", server_date); - expect(__LINE__, "Cookie: name=val\r\n", "http", "e-500s-1000s.com", "/"); - - expt = t; /* expire at past-for-us server date */ - dFree(exp_date); - exp_date = dStrdup(ctime(&expt)); - - string = dStrconcat("name=val; expires=", exp_date, NULL); - a_Cookies_set(string, "e-1000s-1000.com", "/", NULL); - expect(__LINE__, "", "http", "e-1000s-1000.com", "/"); - - a_Cookies_set(string, "e-1000s-1000s.com", "/", server_date); - expect(__LINE__, "", "http", "e-1000s-1000s.com", "/"); - - dFree(server_date); - dFree(exp_date); -} - -static void expires_extremes() -{ - time_t t; - char *server_date; - - a_Cookies_set("name=val; expires=Fri Dec 13 20:45:52 1801", "expmin.com", - "/", NULL); - expect(__LINE__, "", "http", "expmin.com", "/"); - - a_Cookies_set("name=val; expires=Fri Dec 13 20:45:52 1901", "expmin2.com", - "/", NULL); - expect(__LINE__, "", "http", "expmin2.com", "/"); - - a_Cookies_set("name=val; expires=Wed Dec 31 23:59:59 1969", "expneg.com", - "/", NULL); - expect(__LINE__, "", "http", "expneg.com", "/"); - - a_Cookies_set("name=val; expires=Thu, 01-January-70 00:00:00 GMT", - "expepoch.com", "/", NULL); - expect(__LINE__, "", "http", "expepoch.com", "/"); - - /* TODO: revisit these tests in a few decades */ - a_Cookies_set("name=val; expires=Tue Jan 19 03:14:07 2038", "expmax.com", - "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "expmax.com", "/"); - - a_Cookies_set("name=val; expires=Sun January 1 00:00:00 2040", - "pastmax.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "pastmax.com", "/"); - - t = time(NULL)+1000; - server_date = dStrdup(ctime(&t)); - - a_Cookies_set("name=val; expires=Fri Dec 13 20:45:52 1901", "expmina.com", - "/", server_date); - expect(__LINE__, "", "http", "expmina.com", "/"); - - a_Cookies_set("name=val; expires=Wed Dec 31 23:59:59 1969", "expnega.com", - "/", server_date); - expect(__LINE__, "", "http", "expnega.com", "/"); - - a_Cookies_set("name=val; expires=Thu Jan 1 00:00:00 1970", "expepocha.com", - "/", server_date); - expect(__LINE__, "", "http", "expepocha.com", "/"); - - a_Cookies_set("name=val; expires=Tue Jan 19 03:14:07 2038", "expmaxa.com", - "/", server_date); - expect(__LINE__, "Cookie: name=val\r\n", "http", "expmaxa.com", "/"); - - a_Cookies_set("name=val; expires=Thu, 01-Jan-40 00:00:00 GMT", - "pastmaxa.com", "/", server_date); - expect(__LINE__, "Cookie: name=val\r\n", "http", "pastmaxa.com", "/"); - - t = time(NULL)-1000; - dFree(server_date); - server_date = dStrdup(ctime(&t)); - - a_Cookies_set("name=val; expires=Fri Dec 13 20:45:52 1901", "expminb.com", - "/", server_date); - expect(__LINE__, "", "http", "expminb.com", "/"); - - a_Cookies_set("name=val; expires=Wed Dec 31 23:59:59 1969", "expnegb.com", - "/", server_date); - expect(__LINE__, "", "http", "expnegb.com", "/"); - - a_Cookies_set("name=val; expires=Thu Jan 1 00:00:00 1970", "expepochb.com", - "/", server_date); - expect(__LINE__, "", "http", "expepochb.com", "/"); - - a_Cookies_set("name=val; expires=Tue Jan 19 03:14:07 2038", "expmaxb.com", - "/", server_date); - expect(__LINE__, "Cookie: name=val\r\n", "http", "expmaxb.com", "/"); - - a_Cookies_set("name=val; expires=Sun Jan 1 00:00:00 2040", "pastmaxb.com", - "/", server_date); - expect(__LINE__, "Cookie: name=val\r\n", "http", "pastmaxb.com", "/"); - - dFree(server_date); -} - -/* - * On 11 Aug 2009, Dan Winship posted to the http-state list with a bunch of - * date formats he'd gathered. Let's work from that. I'll include his comments - * below in double quotes. - */ -static void expires_date_formats() -{ - /* "Revised Netscape spec format" */ - a_Cookies_set("name=val; expires=Mon, 10-Dec-2037 17:02:24 GMT", - "format1.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "format1.com", "/"); - - /* "rfc1123-date" */ - a_Cookies_set("name=val; expires=Wed, 09 Dec 2037 16:27:23 GMT", - "format2.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "format2.com", "/"); - - /* "4-digit-year version of Netscape spec example (see below). - * Seems to only come from sites using PHP, but it's not PHP - * itself; maybe some framework?" - */ - a_Cookies_set("name=val; expires=Thursday, 01-Jan-2036 00:00:00 GMT", - "format3.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "format3.com", "/"); - - /* "The not-quite-asctime format used by Amazon." */ - a_Cookies_set("name=val; expires=Mon Dec 10 16:32:30 2037 GMT", - "format4.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "format4.com", "/"); - - /* "The syntax used by the example text in the Netscape spec, - * although the actual grammar uses abbreviated weekday names" - */ - a_Cookies_set("name=val; expires=Wednesday, 01-Jan-37 00:00:00 GMT", - "format5.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "format5.com", "/"); - - /* "Original Netscape spec" */ - a_Cookies_set("name=val; expires=Mon, 10-Dec-37 20:35:03 GMT", - "format6.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "format6.com", "/"); - - /* "If this had '01 Jan' it would be an rfc1123-date. This *is* a - * legitimate rfc822 date, though not an rfc2822 date because 'GMT' - * is deprecated in favor of '+0000' there." - */ - a_Cookies_set("name=val; expires=Wed, 1 Jan 2035 00:00:00 GMT", - "format7.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "format7.com", "/"); - - /* "Would match the 'weird php' syntax above if it was '08-Dec'" */ - a_Cookies_set("name=val; expires=Saturday, 8-Dec-2035 21:24:09 GMT", - "format8.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "format8.com", "/"); - - /* "God only knows what they were thinking. This came from a hit-tracker - * site, and it's possible that it's just totally broken and no one parses - * it 'correctly'" - */ - a_Cookies_set("name=val; expires=Thu, 31 Dec 23:55:55 2037 GMT", - "format9.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "format9.com", "/"); - - /* "Another kind of rfc822 / nearly-rfc1123 date, using superfluous - * whitespace." - */ - a_Cookies_set("name=val; expires=Sun, 9 Dec 2036 13:42:05 GMT", - "formata.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "formata.com", "/"); - - /* "Another kind of 'lets throw components together at random'. The - * site that this cookie came has apparently been fixed since then. - * (It uses the Netscape spec format now.)" - */ - a_Cookies_set("name=val; expires=Wed Dec 12 2037 08:44:07 GMT-0500 (EST)", - "formatb.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "formatb.com", "/"); - - a_Cookies_set("name=val; expires=Sun, 1-Jan-2035 00:00:00 GMT", - "formatc.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "formatc.com", "/"); - - /* ...and the remaining handful that he encountered once or twice were - * far too broken to deserve our attention (e.g., times like "13:57:2"). - */ - - /* Now here's what github was sending in 2015. */ - a_Cookies_set("name=val; expires=Sat, 07 Jul 2035 21:41:24 -0000", - "formatd.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "formatd.com", "/"); - -} - -static void path() -{ - a_Cookies_set("name=val; path=/", "p1.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p1.com", "/"); - - a_Cookies_set("name=val; path=/dir1", "p2.com", "/dir2", NULL); - expect(__LINE__, "", "http", "p2.com", "/"); - expect(__LINE__, "", "http", "p2.com", "/d"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p2.com", "/dir1"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p2.com", "/dir1/"); - expect(__LINE__, "", "http", "p2.com", "/dir2"); - expect(__LINE__, "", "http", "p2.com", "/dir11"); - - a_Cookies_set("name=val; path=dir1", "p3.com", "/dir2", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p3.com", "/"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p3.com", "/dir1"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p3.com", "/dir2"); - - a_Cookies_set("name=val; path=/dir1/", "p4.com", "/dir2", NULL); - expect(__LINE__, "", "http", "p4.com", "/"); - /* this next one strikes me as a bit odd, personally, but I suppose it's not - * a big deal */ - expect(__LINE__, "", "http", "p4.com", "/dir1"); - expect(__LINE__, "", "http", "p4.com", "/dir11"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p4.com", "/dir1/"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p4.com", "/dir1/sub"); - - a_Cookies_set("name=val", "p5.com", "/dir/subdir", NULL); - expect(__LINE__, "", "http", "p5.com", "/"); - expect(__LINE__, "", "http", "p5.com", "/bir"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p5.com", "/dir"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p5.com", "/dir/"); - - a_Cookies_set("name=val", "p6.com", "/dir/subdir/", NULL); - expect(__LINE__, "", "http", "p6.com", "/dir/"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p6.com", "/dir/subdir"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "p6.com", "/dir/subdir/s"); -} - -int Cookies_rc_check() -{ - const int line_maxlen = 4096; - FILE *stream; - char *filename; - char line[line_maxlen]; - bool_t default_deny = TRUE; - - /* Get a file pointer */ - filename = dStrconcat(dGethomedir(), "/.dillo/cookiesrc", NULL); - stream = fopen(filename, "r"); - dFree(filename); - - if (!stream) { - MSG_ERR("Cannot run test; cannot open cookiesrc.\n"); - return 1; - } - - /* Get all lines in the file */ - while (!feof(stream)) { - char *rc; - - line[0] = '\0'; - rc = fgets(line, line_maxlen, stream); - if (!rc && ferror(stream)) { - MSG_ERR("Error while reading rule from cookiesrc: %s\n", - dStrerror(errno)); - fclose(stream); - return 2; - } - - /* Remove leading and trailing whitespaces */ - dStrstrip(line); - - if (line[0] != '\0' && line[0] != '#') { - int domain_end, i = 0; - const char *rule; - - /* Get the domain */ - while (line[i] != '\0' && !dIsspace(line[i])) - i++; - domain_end = i; - - /* Skip past whitespace */ - while (dIsspace(line[i])) - i++; - line[domain_end] = '\0'; - - /* Get the rule */ - rule = line + i; - while (line[i] != '\0' && !dIsspace(line[i])) - i++; - line[i] = '\0'; - - if (!dStrAsciiCasecmp(line, "DEFAULT")) { - if (!dStrAsciiCasecmp(rule, "ACCEPT") || - !dStrAsciiCasecmp(rule, "ACCEPT_SESSION")) - default_deny = FALSE; - } else { - if (!dStrAsciiCasecmp(rule, "DENY")) - MSG_WARN("DENY rules in cookiesrc can interfere with test.\n"); - } - } - } - fclose(stream); - - if (default_deny) { - MSG_ERR("Cannot run test with cookiesrc default of deny.\n"); - return 1; - } else { - return 0; - } -} - -int main() -{ - if (Cookies_rc_check()) { - MSG("If you change cookiesrc, remember to stop the DPIs via dpidc.\n"); - return 1; - } - - a_Cookies_set("name=val", "ordinary.com", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "ordinary.com", "/"); - - toomany(); - maxage(); - expires_server_ahead(); - expires_server_behind(); - expires_extremes(); - expires_date_formats(); - - a_Cookies_set("name=val; expires=\"Sun Jan 10 00:00:00 2038\"", - "quoted-date.org", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "quoted-date.org", "/"); - - a_Cookies_set("name=val; expires=\"Sun Jan 11 00:00:00 1970\"", - "quoted-pastdate.org", "/", NULL); - expect(__LINE__, "", "http", "quoted-pastdate.org", "/"); - - path(); - - /* LEADING/TRAILING DOTS AND A LITTLE PUBLIC SUFFIX */ - a_Cookies_set("name=val; domain=co.il", "www.co.il", "/", NULL); - expect(__LINE__, "", "http", "www.co.il", "/"); - - a_Cookies_set("name=val; domain=.co.il", "www.co.il", "/", NULL); - expect(__LINE__, "", "http", "www.co.il", "/"); - - a_Cookies_set("name=val; domain=co.il.", "www.co.il.", "/", NULL); - expect(__LINE__, "", "http", "www.co.il.", "/"); - - a_Cookies_set("name=val; domain=.co.il.", "www.co.il.", "/", NULL); - expect(__LINE__, "", "http", ".www.co.il.", "/"); - - a_Cookies_set("name=val; domain=co.org", "www.co.org", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "www.co.org", "/"); - - a_Cookies_set("name=val; domain=.cp.org", "www.cp.org", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "www.cp.org", "/"); - - - /* DOTDOMAIN */ - a_Cookies_set("name=val; domain=.dotdomain.org", "dotdomain.org", "/", - NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "dotdomain.org", "/"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "www.dotdomain.org", "/"); - - /* HOST_ONLY */ - a_Cookies_set("name=val; domain=.hostonly.org", "hostonly.org", "/", NULL); - a_Cookies_set("name2=val2", "hostonly.org", "/", NULL); - a_Cookies_set("name3=val3; domain=hostonly.org", "hostonly.org", "/", NULL); - expect(__LINE__, "Cookie: name=val; name2=val2; name3=val3\r\n", "http", - "hostonly.org", "/"); - a_Cookies_set("name=new; domain=.hostonly.org", "hostonly.org", "/", NULL); - expect(__LINE__, "Cookie: name=new; name2=val2; name3=val3\r\n", "http", - "hostonly.org", "/"); - a_Cookies_set("name2=new2", "hostonly.org", "/", NULL); - expect(__LINE__, "Cookie: name=new; name2=new2; name3=val3\r\n", "http", - "hostonly.org", "/"); - a_Cookies_set("name3=new3; domain=hostonly.org", "hostonly.org", "/", NULL); - expect(__LINE__, "Cookie: name=new; name2=new2; name3=new3\r\n", "http", - "hostonly.org", "/"); - - /* SUBDOMAIN */ - a_Cookies_set("name=val; domain=www.subdomain.com", "subdomain.com", "/", - NULL); - a_Cookies_set("name=val; domain=.www.subdomain.com", "subdomain.com", "/", - NULL); - expect(__LINE__, "", "http", "subdomain.com", "/"); - expect(__LINE__, "", "http", "www.subdomain.com", "/"); - - /* SUPERDOMAIN(?) */ - a_Cookies_set("name=val; domain=.supdomain.com", "www.supdomain.com", "/", - NULL); - a_Cookies_set("name2=val2; domain=supdomain.com", "www.supdomain.com", "/", - NULL); - expect(__LINE__, "Cookie: name=val; name2=val2\r\n", "http", - "sub2.sub.supdomain.com", "/"); - expect(__LINE__, "Cookie: name=val; name2=val2\r\n", "http", - "www.supdomain.com", "/"); - expect(__LINE__, "Cookie: name=val; name2=val2\r\n", "http", - "supdomain.com", "/"); - - /* UNRELATED */ - a_Cookies_set("name=val; domain=another.com", "unrelated.com", "/", NULL); - expect(__LINE__, "", "http", "another.com", "/"); - a_Cookies_set("name=val; domain=another.com", "a.org", "/", NULL); - expect(__LINE__, "", "http", "another.com", "/"); - a_Cookies_set("name=val; domain=another.com", "badguys.com", "/", NULL); - expect(__LINE__, "", "http", "another.com", "/"); - a_Cookies_set("name=val; domain=another.com", "more.badguys.com", "/", - NULL); - expect(__LINE__, "", "http", "another.com", "/"); - a_Cookies_set("name=val; domain=another.com", "verybadguys.com", "/", NULL); - expect(__LINE__, "", "http", "another.com", "/"); - - a_Cookies_set("name=val; domain=similar.com", "imilar.com", "/", NULL); - a_Cookies_set("name2=val2; domain=similar.com", "ssimilar.com", "/", NULL); - a_Cookies_set("name3=val3; domain=.similar.com", "imilar.com", "/", NULL); - a_Cookies_set("name4=val4; domain=.similar.com", "timilar.com", "/", NULL); - a_Cookies_set("name4=val4; domain=.similar.com", "tiimilar.com", "/", NULL); - expect(__LINE__, "", "http", "similar.com", "/"); - - /* SECURE */ - a_Cookies_set("name=val; secure", "secure.com", "/", NULL); - expect(__LINE__, "", "http", "secure.com", "/"); - expect(__LINE__, "Cookie: name=val\r\n", "https", "secure.com", "/"); - - /* HTTPONLY */ - a_Cookies_set("name=val; HttpOnly", "httponly.net", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "httponly.net", "/"); - - /* GIBBERISH ATTR IGNORED */ - a_Cookies_set("name=val; ldkfals", "gibberish.net", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "gibberish.net", "/"); - - /* WHITESPACE/DELIMITERS */ - a_Cookies_set(" name=val ", "whitespace.net", "/", NULL); - a_Cookies_set("name2=val2;", "whitespace.net", "/", NULL); - expect(__LINE__, "Cookie: name=val; name2=val2\r\n", "http", - "whitespace.net", "/"); - - /* NAMELESS/VALUELESS */ - a_Cookies_set("value", "nonameval.org", "/", NULL); - a_Cookies_set("name=", "nonameval.org", "/", NULL); - a_Cookies_set("name2= ", "nonameval.org", "/", NULL); - expect(__LINE__, "Cookie: name=; name2=\r\n", "http", "nonameval.org", "/"); - a_Cookies_set("=val2", "nonameval.org", "/", NULL); - expect(__LINE__, "Cookie: name=; name2=\r\n", "http", "nonameval.org", "/"); - - - /* SOME IP ADDRS */ - - a_Cookies_set("name=val", "FEDC:BA98:7654:3210:FEDC:BA98:7654:3210", - "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", - "FEDC:BA98:7654:3210:FEDC:BA98:7654:3210", "/"); - - a_Cookies_set("name=val", "::FFFF:129.144.52.38", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "::FFFF:129.144.52.38", - "/"); - - a_Cookies_set("name=val", "127.0.0.1", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "127.0.0.1", "/"); - - a_Cookies_set("name=val; domain=128.0.0.1", "128.0.0.1", "/", NULL); - expect(__LINE__, "Cookie: name=val\r\n", "http", "128.0.0.1", "/"); - - a_Cookies_set("name=val; domain=130.0.0.1", "129.0.0.1", "/", NULL); - expect(__LINE__, "", "http", "129.0.0.1", "/"); - expect(__LINE__, "", "http", "130.0.0.1", "/"); - - a_Cookies_set("name=val", "2.0.0.1", "/", NULL); - a_Cookies_set("name=bad; domain=22.0.0.1", "2.0.0.1", "/", NULL); - a_Cookies_set("name=bad; domain=.0.0.1", "2.0.0.1", "/", NULL); - a_Cookies_set("name=bad; domain=not-ip.org", "2.0.0.1", "/", NULL); - expect(__LINE__, "", "http", "22.0.0.1", "/"); - expect(__LINE__, "", "http", "not-ip.org", "/"); - expect(__LINE__, "Cookie: name=val\r\n", "http", "2.0.0.1", "/"); - -#if 0 -HAD BEEN PLAYING AROUND WITH REAL PUBLIC SUFFIX -a_Cookies_set("name=val;domain=sub.sub.yokohama.jp", "sub.sub.yokohama.jp", "/", NULL); -MSG("sub sub yokohama should work: %s\n", - a_Cookies_get_query("http", "sub.sub.yokohama.jp", "/")); -a_Cookies_set("name=val; domain=sub.tokyo.jp", "sub.sub.tokyo.jp", "/", NULL); -MSG("sub tokyo jp should fail: %s\n", - a_Cookies_get_query("http", "sub.sub.tokyo.jp", "/")); -a_Cookies_set("name=val; domain=pref.chiba.jp", "sub.pref.chiba.jp", "/", NULL); -MSG("pref chiba jp should succeed: %s\n", - a_Cookies_get_query("http", "sub.pref.chiba.jp", "/")); -a_Cookies_set("name=val; domain=org", "www.dillo.org", "/", NULL); -a_Cookies_set("name=val; domain=org", "dillo.org", "/", NULL); -a_Cookies_set("name=val; domain=org", ".dillo.org", "/", NULL); -a_Cookies_set("name=val; domain=org.", ".dillo.org", "/", NULL); -a_Cookies_set("name=val; domain=org.", ".dillo.org.", "/", NULL); -MSG("org should fail: %s\n", - a_Cookies_get_query("http", "www.dillo.org", "/")); -#endif - - MSG("TESTS: passed: %u failed: %u\n", passed, failed); - - MSG("Now that everything is full of fake cookies, you should run " - "'dpidc stop', plus delete cookies.txt if necessary.\n"); - - return 0; -} |