Hello, all. This allows fortune(6) to open fortune files via symlinks. Maybe this is a stupid idea, I dunno, but it seems inconsistent that I can't put a symlink to my fortunes collection in /usr/share/games/fortune and then simply call "fortune foo" instead of "fortune /usr/local/share/games/fortune/ru/foo".
I decided to call readlink(2) explicitly rather than adding check of file type being open, since that resulted in less code. Ah, and yes, I have a port of Russian fortune files pending, but that's for another list and another day. So... okay/notokay anyone? :) -- WBR, Vadim Zhukov Index: fortune.c =================================================================== RCS file: /cvs/src/games/fortune/fortune/fortune.c,v retrieving revision 1.60 diff -u -p -r1.60 fortune.c --- fortune.c 10 Aug 2017 17:00:08 -0000 1.60 +++ fortune.c 14 Dec 2020 22:05:33 -0000 @@ -39,6 +39,7 @@ #include <ctype.h> #include <dirent.h> #include <err.h> +#include <errno.h> #include <fcntl.h> #include <limits.h> #include <locale.h> @@ -388,8 +389,9 @@ add_file(int percent, char *file, char * FILEDESC *parent) { FILEDESC *fp; + ssize_t lnklen; int fd; - char *path, *offensive; + char *path, *offensive, lnkpath[PATH_MAX]; bool was_malloc; bool isdir; @@ -420,8 +422,22 @@ add_file(int percent, char *file, char * } DPRINTF(1, (stderr, "adding file \"%s\"\n", path)); + over: + lnklen = readlink(path, lnkpath, PATH_MAX); + if (lnklen == -1) { + if (errno != EINVAL) + goto openfailed; + } else { + lnkpath[lnklen] = '\0'; + if (was_malloc) + free(path); + path = strdup(lnkpath); + was_malloc = 1; + } + if ((fd = open(path, O_RDONLY)) < 0) { +openfailed: /* * This is a sneak. If the user said -a, and if the * file we're given isn't a file, we check to see if