diff options
| author | Charles <sircharlesaze@gmail.com> | 2020-04-02 20:51:30 +0200 |
|---|---|---|
| committer | Charles <sircharlesaze@gmail.com> | 2020-04-02 20:52:13 +0200 |
| commit | 25d81fe88c7e9aebe011b7b625b4eb7d31936591 (patch) | |
| tree | 9990ee49ac9ad31ea2b6eb45dad285cc398e7e0c | |
| parent | 63e9453f1543cfa98dcb9d2b5078bc919f90d9a9 (diff) | |
| download | ft_printf_test-25d81fe88c7e9aebe011b7b625b4eb7d31936591.tar.gz ft_printf_test-25d81fe88c7e9aebe011b7b625b4eb7d31936591.tar.bz2 ft_printf_test-25d81fe88c7e9aebe011b7b625b4eb7d31936591.zip | |
Added timeout detection
| -rw-r--r-- | Makefile | 16 | ||||
| -rw-r--r-- | README.md | 8 | ||||
| -rw-r--r-- | header.h | 125 | ||||
| -rw-r--r-- | helper.c | 10 | ||||
| -rw-r--r-- | main.c | 12 | ||||
| -rw-r--r-- | prettier.py | 12 | ||||
| -rw-r--r-- | tests/pft_tests.c | 2 |
7 files changed, 118 insertions, 67 deletions
@@ -6,7 +6,7 @@ # By: cacharle <marvin@42.fr> +#+ +:+ +#+ # # +#+#+#+#+#+ +#+ # # Created: 2020/02/06 18:13:15 by cacharle #+# #+# # -# Updated: 2020/02/06 19:50:23 by cacharle ### ########.fr # +# Updated: 2020/04/02 20:50:47 by charles ### ########.fr # # # # **************************************************************************** # @@ -69,35 +69,33 @@ generatebonus: .PHONY: check_leaks check_leaks: - $(CC) $(LDFLAGS) $(CCFLAGS) -g -o $(CHECK_LEAKS_NAME) check_leaks.c + $(CC) $(CCFLAGS) -g -o $(CHECK_LEAKS_NAME) check_leaks.c $(LDFLAGS) valgrind ./$(CHECK_LEAKS_NAME) > /dev/null check_leaks_verbose: - $(CC) $(LDFLAGS) $(CCFLAGS) -g -o $(CHECK_LEAKS_NAME) check_leaks.c + $(CC) $(CCFLAGS) -g -o $(CHECK_LEAKS_NAME) check_leaks.c $(LDFLAGS) valgrind --leak-check=full ./$(CHECK_LEAKS_NAME) > /dev/null -all: ft_printf_all $(NAME) +all: $(NAME) allbonus: CCFLAGS += -D FT_PRINTF_TEST_BONUS allbonus: ft_printf_all ft_printf_bonus $(NAME) -$(NAME): $(OBJ) header.h tests/tests.h - $(CC) $(LDFLAGS) $(CCFLAGS) -o $@ $(OBJ) +$(NAME): ft_printf_all $(OBJ) + $(CC) $(CCFLAGS) -o $@ $(OBJ) $(LDFLAGS) -%.o: %.c +%.o: %.c header.h tests/tests.h $(CC) $(CCFLAGS) -c -o $@ $< clean: $(RM) $(OBJ) - $(MAKE) -C $(FT_PRINTF_PATH) clean fclean: clean $(RM) $(NAME) $(MAKE) -C $(FT_PRINTF_PATH) fclean re: fclean all - $(MAKE) -C $(FT_PRINTF_PATH) re ft_printf_all: $(MAKE) -C $(FT_PRINTF_PATH) all @@ -21,7 +21,7 @@ or modify the `FT_PRINTF_PATH` variable in the Makefile - `> make quiet`: to show a more quiet output - `> make raw`: run the tests in a ugly but parsable format - `> python3 prettier -h`: show prettier options -- `> make generate`: generate 100 random test +- `> make generate`: generate 100 random test ### Bonus @@ -48,12 +48,6 @@ locally if you don't have root access. You can then run `> brew install valgrind - `> make check_leaks`: run valgrind on a test (without the test themself). - `> make check_leaks_verbose`: add `--leak-check=full` to valgrind. -## Pro tips - -This doesnt handle timeout, so if your `ft_printf` goes in an infinite loop, -this test will too. -`Ctrl-C` is your best friend. - ## Credits - [moulitest](https://github.com/yyang42/moulitest) by yyang42 @@ -6,13 +6,14 @@ /* By: cacharle <marvin@42.fr> +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2020/02/06 18:13:32 by cacharle #+# #+# */ -/* Updated: 2020/02/21 01:21:48 by cacharle ### ########.fr */ +/* Updated: 2020/04/02 20:49:26 by charles ### ########.fr */ /* */ /* ************************************************************************** */ #ifndef FT_PRINTF_TEST_HEADER_H # define FT_PRINTF_TEST_HEADER_H +# include <sys/select.h> # include <sys/wait.h> # include <stdlib.h> # include <stdio.h> @@ -21,6 +22,7 @@ # include <stdbool.h> int pid; +int pid2; bool signaled; static bool origin_signaled = false; static bool user_signaled = false; @@ -29,6 +31,18 @@ int user_ret; char *origin_buf; char *user_buf; +struct timeval timeout; +fd_set input_set; +int timeout_pipe[2]; +int fd_read_num; + +#define PIPE_WRITE 1 +#define PIPE_READ 0 + +// #define PRINTF_NULL_STR "(nil)" + +// int printf_wrapper(const char *format, ...); + void generated_test(void); void saved_test(void); @@ -37,6 +51,7 @@ int ft_printf(const char *format, ...); void print_buf_ko(char *msg); void print_ret_ko(char *msg); void print_signaled_ko(char *msg); +void print_timeouted(char *msg); void print_ok(void); void print_ko(void); void ft_putstr_non_printable(char *str); @@ -45,50 +60,78 @@ void test_setup(void); void test_tear_down(void); char *read_stdout_buf(void); -# define TEST_SEGFAULT(x) do { \ - if ((pid = fork()) < 0) \ - exit(EXIT_FAILURE); \ - if (pid == 0) { \ - do { x } while(0); \ - exit(EXIT_SUCCESS); \ - } else { \ - wait(&pid); \ - signaled = WIFSIGNALED(pid); \ - } \ +char fd_buf[10]; + +# define TEST_TIMEOUT(x) do { \ + if ((pid2 = fork()) == -1) \ + exit(EXIT_FAILURE); \ + if (pid2 == 0) { \ + do { x; } while (0); \ + write(timeout_pipe[PIPE_WRITE], "a", 1); \ + exit(EXIT_SUCCESS); \ + } \ + FD_ZERO(&input_set); \ + FD_SET(timeout_pipe[PIPE_READ], &input_set); \ + fd_read_num = select(FD_SETSIZE, &input_set, NULL, NULL, &timeout); \ + if (fd_read_num == -1) \ + exit(EXIT_FAILURE); \ + if (fd_read_num == 0) \ + kill(pid2, 9); \ + else { \ + wait(&pid2); \ + read(timeout_pipe[PIPE_READ], fd_buf, 1); \ + } \ +} while (0); + +# define TEST_SEGFAULT(x) do { \ + if ((pid = fork()) < 0) \ + exit(EXIT_FAILURE); \ + if (pid == 0) { \ + do { x } while(0); \ + exit(EXIT_SUCCESS); \ + } \ + wait(&pid); \ + signaled = WIFSIGNALED(pid); \ } while(0); -# define TEST_PRINTF(...) do { \ - test_setup(); \ - TEST_SEGFAULT( \ - origin_ret = printf(__VA_ARGS__); \ - ); \ - origin_buf = strdup(read_stdout_buf()); \ - origin_signaled = signaled; \ - TEST_SEGFAULT( \ - user_ret = ft_printf(__VA_ARGS__); \ - ); \ - user_buf = strdup(read_stdout_buf()); \ - user_signaled = signaled; \ - test_tear_down(); \ +# define TEST_PRINTF(...) do { \ + test_setup(); \ + TEST_SEGFAULT( \ + origin_ret = printf(__VA_ARGS__); \ + ); \ + origin_buf = strdup(read_stdout_buf()); \ + origin_signaled = signaled; \ + fd_read_num = 1; \ + TEST_SEGFAULT( \ + TEST_TIMEOUT(user_ret = ft_printf(__VA_ARGS__)); \ + ); \ + user_buf = strdup(read_stdout_buf()); \ + user_signaled = signaled; \ + test_tear_down(); \ } while (0) -# define ASSERT_PRINTF(...) do { \ - TEST_PRINTF(__VA_ARGS__); \ - if (!origin_signaled && user_signaled) \ - print_signaled_ko(#__VA_ARGS__); \ - else if (origin_signaled && user_signaled) \ - print_ok(); \ - else if (!origin_signaled && !user_signaled) { \ - if (memcmp(origin_buf, user_buf, \ - strlen(origin_buf) + 1) != 0) \ - print_buf_ko(#__VA_ARGS__); \ - else if (origin_ret != user_ret) \ - print_ret_ko(#__VA_ARGS__); \ - else \ - print_ok(); \ - } \ - if (!origin_signaled) free(origin_buf); \ - if (!user_signaled) free(user_buf); \ +# define ASSERT_PRINTF(...) do { \ + TEST_PRINTF(__VA_ARGS__); \ + if (fd_read_num == 0) \ + print_timeouted(#__VA_ARGS__); \ + else \ + { \ + if (!origin_signaled && user_signaled) \ + print_signaled_ko(#__VA_ARGS__); \ + else if (origin_signaled && user_signaled) \ + print_ok(); \ + else if (!origin_signaled && !user_signaled) { \ + if (memcmp(origin_buf, user_buf, \ + strlen(origin_buf) + 1) != 0) \ + print_buf_ko(#__VA_ARGS__); \ + else if (origin_ret != user_ret) \ + print_ret_ko(#__VA_ARGS__); \ + else \ + print_ok(); \ + } \ + } \ + free(origin_buf); \ + free(user_buf); \ } while(0); #endif @@ -6,7 +6,7 @@ /* By: cacharle <marvin@42.fr> +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2020/02/06 18:13:38 by cacharle #+# #+# */ -/* Updated: 2020/02/21 01:14:37 by cacharle ### ########.fr */ +/* Updated: 2020/04/02 20:31:04 by charles ### ########.fr */ /* */ /* ************************************************************************** */ @@ -24,6 +24,8 @@ char buf[BUF_SIZE + 1] = {0}; void test_setup(void) { + origin_buf = NULL; + user_buf = NULL; if (saved_stdout != -1) test_tear_down(); saved_stdout = dup(STDOUT_FILENO); @@ -80,6 +82,12 @@ void print_signaled_ko(char *msg) fflush(stdout); } +void print_timeouted(char *msg) +{ + printf("FAIL/TIMEOUT<>ARGS:%s<>EXPECTED:<>ACTUAL:\n", msg); + fflush(stdout); +} + inline void print_ok(void) { printf("OK\n"); fflush(stdout); } void ft_putstr_non_printable(char *str) @@ -6,7 +6,7 @@ /* By: cacharle <marvin@42.fr> +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2020/02/06 18:13:45 by cacharle #+# #+# */ -/* Updated: 2020/02/26 17:33:55 by cacharle ### ########.fr */ +/* Updated: 2020/04/02 20:46:17 by charles ### ########.fr */ /* */ /* ************************************************************************** */ @@ -16,11 +16,19 @@ int main(int argc, char **argv) { + timeout.tv_sec = 1; + timeout.tv_usec = 0; + if (pipe(timeout_pipe) == -1) + return (1); + (void)argc; (void)argv; + + timeout.tv_sec = 0; + timeout.tv_usec = 100000; test_pft_nacked(); test_pft_percent(); - /* test_pft_nocrash(); */ + test_pft_nocrash(); test_pft_string(); test_pft_int_i(); test_pft_int_d(); diff --git a/prettier.py b/prettier.py index 1b30db1..aaf19b3 100644 --- a/prettier.py +++ b/prettier.py @@ -6,7 +6,7 @@ # By: cacharle <marvin@42.fr> +#+ +:+ +#+ # # +#+#+#+#+#+ +#+ # # Created: 2020/02/06 18:13:52 by cacharle #+# #+# # -# Updated: 2020/02/06 18:13:54 by cacharle ### ########.fr # +# Updated: 2020/04/02 19:55:29 by charles ### ########.fr # # # # **************************************************************************** # @@ -56,12 +56,12 @@ def parse(options): for line in sys.stdin: sys.stdout.flush() line = line.strip() - if line == "OK": - logs["ok"] += 1 - print(green("."), end="") - continue - m = re.search("^FAIL/(OUTPUT|RETURN|SEGFAULT)<>ARGS:(.*)<>EXPECTED:(.*)<>ACTUAL:(.*)$", line) + m = re.search("^FAIL/(OUTPUT|RETURN|SEGFAULT|TIMEOUT)<>ARGS:(.*)<>EXPECTED:(.*)<>ACTUAL:(.*)$", line) if m is None: + if line == "OK": + logs["ok"] += 1 + print(green("."), end="") + continue print(line) print("PARSING ERROR") continue diff --git a/tests/pft_tests.c b/tests/pft_tests.c index 04f9dcc..3f29604 100644 --- a/tests/pft_tests.c +++ b/tests/pft_tests.c @@ -6,7 +6,7 @@ /* By: cacharle <marvin@42.fr> +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2020/02/06 18:15:10 by cacharle #+# #+# */ -/* Updated: 2020/02/26 17:31:23 by cacharle ### ########.fr */ +/* Updated: 2020/04/02 20:46:35 by charles ### ########.fr */ /* */ /* ************************************************************************** */ |
