Hi, 

Here is an updated version of the unveil patch. 

I think almost everything on the to-do list was completed, except
searching for a custom wget location. I don't see an especially easy
way of doing that, and it seems an unlikely edge-case for someone to
remove wget from the system default location. 

- Permissions have been tightened in dpis
- Checking for AUTHORITY env, fallback to ~/.Xauthority
- Prefs parser is aware of 'enable_unveil'
- Fix some non-strict code warnings
- dillorc 'enable_unveil' default setting
- Formatting, whitespace fixes
- ...

I have done a fair amount of testing and it works for me. Unless there
is any further feedback or interest, I will leave it as-is for now.

Regards,
Alex


diff -upr a/configure.ac b/configure.ac
--- a/configure.ac      Sun Aug 11 22:21:59 2024
+++ b/configure.ac      Tue Aug 20 19:08:02 2024
@@ -36,6 +36,11 @@ AC_ARG_ENABLE([insure],
   [enable_insure=$enableval],
   [enable_insure=no])
 
+AC_ARG_ENABLE([unveil],
+  [AS_HELP_STRING([--enable-unveil], [Build with support for unveil])],
+  [enable_unveil=$enableval],
+  [enable_unveil=no])
+
 AC_ARG_ENABLE([ipv6],
   [AS_HELP_STRING([--enable-ipv6], [Build with support for IPv6])],
   [enable_ipv6=$enableval],
@@ -619,6 +624,9 @@ if test "x$enable_insure" = "xyes" ; then
   CC="insure -Zoi \"compiler $CC\""
   LIBS="$LIBS -lstdc++-2-libc6.1-1-2.9.0"
 fi
+if test "x$enable_unveil" = "xyes" ; then
+  AC_DEFINE([ENABLE_UNVEIL], [1], [Enable unveil])
+fi
 if test "x$enable_threaded_dns" = "xyes" ; then
   CFLAGS="$CFLAGS -DD_DNS_THREADED"
 fi
@@ -726,4 +734,5 @@ _AS_ECHO([  GIF enabled    : ${enable_gif}])
 _AS_ECHO([  SVG enabled    : ${enable_svg}])
 _AS_ECHO([])
 _AS_ECHO([  HTML tests     : ${html_tests_ok}])
+_AS_ECHO([  unveil enabled : ${enable_unveil}])
 _AS_ECHO([])
diff -upr a/dillorc b/dillorc
--- a/dillorc   Sun Aug 11 22:21:59 2024
+++ b/dillorc   Tue Aug 20 19:08:02 2024
@@ -46,6 +46,9 @@
 # height of the visible page area.
 #scroll_step=100
 
+# Enable unveil security feature (currently only available on OpenBSD)
+#enable_unveil=NO
+
 #-------------------------------------------------------------------------
 #                           RENDERING SECTION
 #-------------------------------------------------------------------------
diff -upr a/dlib/dlib.c b/dlib/dlib.c
--- a/dlib/dlib.c       Sun Aug 11 22:21:59 2024
+++ b/dlib/dlib.c       Tue Aug 20 19:08:02 2024
@@ -922,6 +922,100 @@ char *dGethomedir (void)
 }
 
 /**
+ * Return the save directory in a static string
+ */
+char *dGetsavedir (void)
+{
+   static char *dillorc = NULL;
+   dillorc = dStrconcat(dGethomedir(), "/", ".dillo/dillorc", NULL);
+   FILE *In;
+   int len;
+   char *rcline = NULL, *value = NULL, *p;
+   if ((In = fopen(dillorc, "r")) == NULL) {
+      DLIB_MSG("dGetsavedir: unable to open dillorc.\n");
+      return (NULL);
+   }
+   while ((rcline = dGetline(In)) != NULL) {
+      if (strncmp(rcline, "save_dir", 8) == 0)
+         break;
+      dFree(rcline);
+   }
+   fclose(In);
+   if (!rcline) {
+      value = NULL;
+      DLIB_MSG("dGetsavedir: no 'save_dir' in dillorc..\n");
+   } else {
+      len = (int) strlen(rcline);
+      if (len && rcline[len - 1] == '\n')
+         rcline[len - 1] = 0;
+      if ((p = strchr(rcline, '='))) {
+         while (*++p == ' ');
+         value = dStrdup(p);
+      } else {
+         value = NULL;
+        DLIB_MSG("dGetsavedir: error parsing value in dillorc.\n");
+      }
+   }
+   dFree(rcline);
+   return (value);
+}
+
+/**
+ * Return the enable_unveil value in a static string
+ */
+char *dGetenableunveil (void)
+{
+   static char *dillorc = NULL;
+   dillorc = dStrconcat(dGethomedir(), "/", ".dillo/dillorc", NULL);
+   FILE *In;
+   int len;
+   char *rcline = NULL, *value = NULL, *p;
+   if ((In = fopen(dillorc, "r")) == NULL) {
+      DLIB_MSG("dGetenableunveil: unable to open dillorc.\n");
+      return (NULL);
+   }
+   while ((rcline = dGetline(In)) != NULL) {
+      if (strncmp(rcline, "enable_unveil", 13) == 0)
+         break;
+      dFree(rcline);
+   }
+   fclose(In);
+   if (!rcline) {
+      value = NULL;
+      DLIB_MSG("dGetenableunveil: no 'enable_unveil' in dillorc.\n");
+   } else {
+      len = (int) strlen(rcline);
+      if (len && rcline[len - 1] == '\n')
+         rcline[len - 1] = 0;
+      if ((p = strchr(rcline, '='))) {
+         while (*++p == ' ');
+         value = dStrdup(p);
+      } else {
+         value = NULL;
+        DLIB_MSG("dGetenableunveil: error parsing value in dillorc.\n");
+      }
+   }
+   dFree(rcline);
+   return (value);
+}
+
+/**
+ * Use unveil on OpenBSD
+ */
+void *dUnveil(const char *path, const char *perm)
+{
+    #ifdef ENABLE_UNVEIL
+    #ifdef __OpenBSD__
+    int unveil(const char *path, const char *permissions);
+    if (unveil(path, perm) == -1) {
+       DLIB_MSG("unveil(%s, %s) failed: %s\n", path, perm, strerror(errno));
+       exit(1);
+    }
+    #endif
+    #endif
+}
+
+/**
  * Get a line from a FILE stream.
  * Return value: read line on success, NULL on EOF.
  */
diff -upr a/dlib/dlib.h b/dlib/dlib.h
--- a/dlib/dlib.h       Sun Aug 11 22:21:59 2024
+++ b/dlib/dlib.h       Tue Aug 20 19:08:02 2024
@@ -175,6 +175,9 @@ void dLib_show_messages(bool_t show);
  */
 char *dGetcwd(void);
 char *dGethomedir(void);
+char *dGetsavedir(void);
+char *dGetenableunveil(void);
+void *dUnveil(const char *path, const char *perm);
 char *dGetline(FILE *stream);
 int dClose(int fd);
 int dUsleep(unsigned long us);
diff -upr a/dpi/bookmarks.c b/dpi/bookmarks.c
--- a/dpi/bookmarks.c   Sun Aug 11 22:21:59 2024
+++ b/dpi/bookmarks.c   Tue Aug 20 19:08:02 2024
@@ -37,6 +37,7 @@
 #include <signal.h>
 #include "../dpip/dpip.h"
 #include "dpiutil.h"
+#include "../dlib/dlib.h"
 
 
 /*
@@ -1606,7 +1607,6 @@ static void termination_handler(int signum)
   exit(signum);
 }
 
-
 /*
  * -- MAIN -------------------------------------------------------------------
  */
@@ -1616,6 +1616,21 @@ int main(void) {
    socklen_t address_size;
    char *tok;
    Dsh *sh;
+
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         char *dil_bm = dStrconcat(dGethomedir(), "/.dillo/bm.txt", NULL);
+         dUnveil(dil_bm, "rwc");
+         dFree(dil_bm);
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+         dUnveil(dil_loc, "r");
+         dFree(dil_loc);
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
 
    /* Arrange the cleanup function for terminations via exit() */
    atexit(cleanup);
diff -upr a/dpi/cookies.c b/dpi/cookies.c
--- a/dpi/cookies.c     Sun Aug 11 22:21:59 2024
+++ b/dpi/cookies.c     Tue Aug 20 19:08:02 2024
@@ -50,6 +50,7 @@ int main(void)
 #include <signal.h>
 #include "dpiutil.h"
 #include "../dpip/dpip.h"
+#include "../dlib/dlib.h"
 
 
 /*
@@ -1632,7 +1633,6 @@ static void termination_handler(int signum)
   exit(signum);
 }
 
-
 /*
  * -- MAIN -------------------------------------------------------------------
  */
@@ -1643,7 +1643,22 @@ int main(void) {
    int sock_fd, code;
    char *buf;
    Dsh *sh;
-
+   
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         char *cookiesrc_loc = dStrconcat(dGethomedir(), "/.dillo/cookiesrc", 
NULL);
+         dUnveil(cookiesrc_loc, "rwc");
+         dFree(cookiesrc_loc);
+         char *cookies_loc = dStrconcat(dGethomedir(), "/.dillo/cookies.txt", 
NULL);
+         dUnveil(cookies_loc, "rwc");
+         dFree(cookies_loc);
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
+   
    /* Arrange the cleanup function for terminations via exit() */
    atexit(cleanup);
 
diff -upr a/dpi/datauri.c b/dpi/datauri.c
--- a/dpi/datauri.c     Sun Aug 11 22:21:59 2024
+++ b/dpi/datauri.c     Tue Aug 20 19:08:02 2024
@@ -21,6 +21,7 @@
 #include "../dpip/dpip.h"
 #include "dpiutil.h"
 #include "../src/misc.h"
+#include "../dlib/dlib.h"
 
 /*
  * Debugging macros
@@ -290,6 +291,19 @@ int main(void)
    unsigned char *data;
    int rc;
    size_t data_size = 0;
+   
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL  
+         dUnveil("/tmp", "rwc");
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo/dpid_comm_keys", 
NULL);
+         dUnveil(dil_loc, "rwc");
+         dFree(dil_loc);
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
 
    /* Initialize the SockHandler */
    sh = a_Dpip_dsh_new(STDIN_FILENO, STDOUT_FILENO, 8*1024);
diff -upr a/dpi/downloads.cc b/dpi/downloads.cc
--- a/dpi/downloads.cc  Sun Aug 11 22:21:59 2024
+++ b/dpi/downloads.cc  Tue Aug 20 19:08:13 2024
@@ -45,6 +45,7 @@
 #include "config.h"
 #include "dpiutil.h"
 #include "../dpip/dpip.h"
+#include "../dlib/dlib.h"
 
 /*
  * Debugging macros
@@ -206,7 +207,6 @@ static char *escape_tooltip(const char *buf, ssize_t l
    return ret;
 }
 
-
 /*
  * Global variables
  */
@@ -1098,13 +1098,37 @@ static void custLabelMeasure(const Fl_Label* o, int& W
    fl_measure(o->value, W, H, interpret_symbols);
 }
 
-
-
 //int main(int argc, char **argv)
 int main()
 {
    int ww = 420, wh = 85;
-
+   
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         dUnveil("/tmp", "rwc");
+         dUnveil("/etc/fonts", "r");
+         dUnveil("/usr/local/bin/wget", "x");
+         char *xauth_loc = dStrconcat(dGethomedir(), "/.Xauthority", NULL);
+         char *xauth = getenv("AUTHORITY");
+         if (xauth && strlen(xauth)) {
+            dUnveil(xauth, "r");
+            } else {
+                   dUnveil(xauth_loc, "r");
+                  } 
+         dFree(xauth_loc);
+         dFree(xauth); 
+         dUnveil("/usr/local/share/fonts", "r");
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+         dUnveil(dil_loc, "r");
+         dFree(dil_loc);
+         dUnveil(dGetsavedir(), "rw");
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
+   
    Fl::lock();
 
    // Disable '@' and '&' interpretation in normal labels.
diff -upr a/dpi/file.c b/dpi/file.c
--- a/dpi/file.c        Sun Aug 11 22:21:59 2024
+++ b/dpi/file.c        Tue Aug 20 19:08:02 2024
@@ -37,6 +37,7 @@
 #include "../dpip/dpip.h"
 #include "dpiutil.h"
 #include "d_size.h"
+#include "../dlib/dlib.h"
 
 /*
  * Debugging macros
@@ -1063,12 +1064,31 @@ static int File_check_fds(uint_t seconds)
    return st;
 }
 
-
 int main(void)
 {
    struct sockaddr_in sin;
    socklen_t sin_sz;
    int sock_fd, c_st, st = 1;
+
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         dUnveil(dGetsavedir(), "r");
+         dUnveil("/tmp", "rw");
+         char *home_loc = dStrconcat(dGethomedir(), "", NULL);
+         dUnveil(home_loc, "r");
+         dFree(home_loc);
+         char *ssh_loc = dStrconcat(dGethomedir(), "/.ssh", NULL);
+         dUnveil(ssh_loc, "");
+         dFree(ssh_loc);
+         char *config_loc = dStrconcat(dGethomedir(), "/.config", NULL);
+         dUnveil(config_loc, "");
+         dFree(config_loc);
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
 
    /* Arrange the cleanup function for abnormal terminations */
    if (signal (SIGINT, termination_handler) == SIG_IGN)
diff -upr a/dpi/ftp.c b/dpi/ftp.c
--- a/dpi/ftp.c Sun Aug 11 22:21:59 2024
+++ b/dpi/ftp.c Tue Aug 20 19:08:02 2024
@@ -44,6 +44,7 @@
 #include "../dpip/dpip.h"
 #include "dpiutil.h"
 #include "d_size.h"
+#include "../dlib/dlib.h"
 
 /*
  * Debugging macros
@@ -282,6 +283,21 @@ int main(int argc, char **argv)
    int st, rc;
    char *p, *d_cmd;
 
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         dUnveil("/tmp", "rwc");
+         dUnveil("/usr/local/bin/wget", "x");
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+         dUnveil(dil_loc, "r");
+         dFree(dil_loc);
+         dUnveil(dGetsavedir(), "rwc");
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
+   
    /* wget may need to write a temporary file... */
    rc = chdir("/tmp");
    if (rc == -1) {
diff -upr a/dpi/vsource.c b/dpi/vsource.c
--- a/dpi/vsource.c     Sun Aug 11 22:21:59 2024
+++ b/dpi/vsource.c     Tue Aug 20 19:08:02 2024
@@ -21,6 +21,7 @@
 #include <errno.h>
 #include "../dpip/dpip.h"
 #include "dpiutil.h"
+#include "../dlib/dlib.h"
 
 /*
  * Debugging macros
@@ -188,6 +189,18 @@ int main(void)
    char *dpip_tag, *cmd = NULL, *cmd2 = NULL, *url = NULL, *size_str = NULL;
    char *d_cmd;
 
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+         dUnveil(dil_loc, "r");
+         dFree(dil_loc);
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
+   
    _MSG("starting...\n");
    //sleep(20);
 
diff -upr a/dpid/main.c b/dpid/main.c
--- a/dpid/main.c       Sun Aug 11 22:21:59 2024
+++ b/dpid/main.c       Tue Aug 20 19:08:02 2024
@@ -236,6 +236,19 @@ int main(void)
    //daemon(0,0); /* Use 0,1 for feedback */
    /* TODO: call setsid() ?? */
 
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         dUnveil("/usr/local/lib/dillo", "rx");
+         dUnveil("/usr/local/etc/dillo", "r");
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+         dUnveil(dil_loc, "rwc");
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
+   
    /* Allow read and write access, but only for the user.
     * TODO: can this cause trouble with umount? */
    umask(0077);
diff -upr a/src/dillo.cc b/src/dillo.cc
--- a/src/dillo.cc      Sun Aug 11 22:21:59 2024
+++ b/src/dillo.cc      Tue Aug 20 19:08:02 2024
@@ -463,7 +463,53 @@ int main(int argc, char **argv)
       fclose(fp);
    }
    dLib_show_messages(prefs.show_msg);
-
+   
+   // Use unveil
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         const char *home = dGethomedir();
+          const char *save = prefs.save_dir;
+          int nsave = strlen(save);
+          int nhome = strlen(home);
+          if (nsave <= nhome) {
+             /* Prevent save_dir="/home" and save_dir=$HOME */
+             if (strncmp(save, home, nsave) == 0) {
+                MSG("save_dir cannot contain home\n");
+                exit(1);
+                }
+          }
+          dUnveil("/usr/local/share/fonts", "r");
+          dUnveil("/usr/local/share/icons", "r");
+          dUnveil("/usr/X11R6/share/X11/locale", "r");
+          dUnveil("/usr/X11R6/lib/X11/fonts", "r");
+          dUnveil("/usr/local/etc/dillo", "r");
+          dUnveil("/tmp", "rwc");
+          dUnveil("/usr/local/bin/dpid", "x");
+          dUnveil("/etc/fonts", "r");
+          dUnveil("/etc/resolv.conf", "r");
+          dUnveil("/etc/ssl/cert.pem", "r");
+          dUnveil(prefs.save_dir, "rwc");
+          char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+          dUnveil(dil_loc, "rwc");
+          dFree(dil_loc);
+          char *icons_loc = dStrconcat(dGethomedir(), "/.icons", NULL);
+          dUnveil(icons_loc, "r");
+          dFree(icons_loc);
+          char *xauth_loc = dStrconcat(dGethomedir(), "/.Xauthority", NULL);
+          char *xauth = getenv("AUTHORITY");
+                if (xauth && strlen(xauth)) {
+                    dUnveil(xauth, "r");
+                   } else {
+                           dUnveil(xauth_loc, "r");
+                          } 
+          dFree(xauth_loc);
+          dFree(xauth); 
+          dUnveil(NULL, NULL);
+          #endif
+       } 
+    }
+    
    // initialize internal modules
    a_Dpi_init();
    a_Dns_init();
diff -upr a/src/prefs.c b/src/prefs.c
--- a/src/prefs.c       Sun Aug 11 22:21:59 2024
+++ b/src/prefs.c       Tue Aug 20 19:08:02 2024
@@ -72,6 +72,7 @@ void a_Prefs_init(void)
    prefs.http_strict_transport_security = TRUE;
    prefs.http_force_https = FALSE;
    prefs.http_user_agent = dStrdup(PREFS_HTTP_USER_AGENT);
+   prefs.enable_unveil = FALSE;
    prefs.limit_text_width = FALSE;
    prefs.adjust_min_width = TRUE;
    prefs.adjust_table_min_width = TRUE;
diff -upr a/src/prefs.h b/src/prefs.h
--- a/src/prefs.h       Sun Aug 11 22:21:59 2024
+++ b/src/prefs.h       Tue Aug 20 19:08:02 2024
@@ -100,6 +100,7 @@ typedef struct {
    bool_t http_persistent_conns;
    bool_t http_strict_transport_security;
    bool_t http_force_https;
+   bool_t enable_unveil;
    int32_t buffered_drawing;
    char *font_serif;
    char *font_sans_serif;
diff -upr a/src/prefsparser.cc b/src/prefsparser.cc
--- a/src/prefsparser.cc        Sun Aug 11 22:21:59 2024
+++ b/src/prefsparser.cc        Tue Aug 20 19:08:02 2024
@@ -182,6 +182,7 @@ void PrefsParser::parse(FILE *fp)
         PREFS_BOOL, 0 },
       { "http_force_https", &prefs.http_force_https, PREFS_BOOL, 0 },
       { "http_user_agent", &prefs.http_user_agent, PREFS_STRING, 0 },
+      { "enable_unveil", &prefs.enable_unveil, PREFS_BOOL, 0 },
       { "limit_text_width", &prefs.limit_text_width, PREFS_BOOL, 0 },
       { "adjust_min_width", &prefs.adjust_min_width, PREFS_BOOL, 0 },
       { "adjust_table_min_width", &prefs.adjust_table_min_width, PREFS_BOOL, 0 
},
diff -upr a/configure.ac b/configure.ac
--- a/configure.ac	Sun Aug 11 22:21:59 2024
+++ b/configure.ac	Tue Aug 20 19:08:02 2024
@@ -36,6 +36,11 @@ AC_ARG_ENABLE([insure],
   [enable_insure=$enableval],
   [enable_insure=no])
 
+AC_ARG_ENABLE([unveil],
+  [AS_HELP_STRING([--enable-unveil], [Build with support for unveil])],
+  [enable_unveil=$enableval],
+  [enable_unveil=no])
+
 AC_ARG_ENABLE([ipv6],
   [AS_HELP_STRING([--enable-ipv6], [Build with support for IPv6])],
   [enable_ipv6=$enableval],
@@ -619,6 +624,9 @@ if test "x$enable_insure" = "xyes" ; then
   CC="insure -Zoi \"compiler $CC\""
   LIBS="$LIBS -lstdc++-2-libc6.1-1-2.9.0"
 fi
+if test "x$enable_unveil" = "xyes" ; then
+  AC_DEFINE([ENABLE_UNVEIL], [1], [Enable unveil])
+fi
 if test "x$enable_threaded_dns" = "xyes" ; then
   CFLAGS="$CFLAGS -DD_DNS_THREADED"
 fi
@@ -726,4 +734,5 @@ _AS_ECHO([  GIF enabled    : ${enable_gif}])
 _AS_ECHO([  SVG enabled    : ${enable_svg}])
 _AS_ECHO([])
 _AS_ECHO([  HTML tests     : ${html_tests_ok}])
+_AS_ECHO([  unveil enabled : ${enable_unveil}])
 _AS_ECHO([])
diff -upr a/dillorc b/dillorc
--- a/dillorc	Sun Aug 11 22:21:59 2024
+++ b/dillorc	Tue Aug 20 19:08:02 2024
@@ -46,6 +46,9 @@
 # height of the visible page area.
 #scroll_step=100
 
+# Enable unveil security feature (currently only available on OpenBSD)
+#enable_unveil=NO
+
 #-------------------------------------------------------------------------
 #                           RENDERING SECTION
 #-------------------------------------------------------------------------
diff -upr a/dlib/dlib.c b/dlib/dlib.c
--- a/dlib/dlib.c	Sun Aug 11 22:21:59 2024
+++ b/dlib/dlib.c	Tue Aug 20 19:08:02 2024
@@ -922,6 +922,100 @@ char *dGethomedir (void)
 }
 
 /**
+ * Return the save directory in a static string
+ */
+char *dGetsavedir (void)
+{
+   static char *dillorc = NULL;
+   dillorc = dStrconcat(dGethomedir(), "/", ".dillo/dillorc", NULL);
+   FILE *In;
+   int len;
+   char *rcline = NULL, *value = NULL, *p;
+   if ((In = fopen(dillorc, "r")) == NULL) {
+      DLIB_MSG("dGetsavedir: unable to open dillorc.\n");
+      return (NULL);
+   }
+   while ((rcline = dGetline(In)) != NULL) {
+      if (strncmp(rcline, "save_dir", 8) == 0)
+         break;
+      dFree(rcline);
+   }
+   fclose(In);
+   if (!rcline) {
+      value = NULL;
+      DLIB_MSG("dGetsavedir: no 'save_dir' in dillorc..\n");
+   } else {
+      len = (int) strlen(rcline);
+      if (len && rcline[len - 1] == '\n')
+         rcline[len - 1] = 0;
+      if ((p = strchr(rcline, '='))) {
+         while (*++p == ' ');
+         value = dStrdup(p);
+      } else {
+         value = NULL;
+	 DLIB_MSG("dGetsavedir: error parsing value in dillorc.\n");
+      }
+   }
+   dFree(rcline);
+   return (value);
+}
+
+/**
+ * Return the enable_unveil value in a static string
+ */
+char *dGetenableunveil (void)
+{
+   static char *dillorc = NULL;
+   dillorc = dStrconcat(dGethomedir(), "/", ".dillo/dillorc", NULL);
+   FILE *In;
+   int len;
+   char *rcline = NULL, *value = NULL, *p;
+   if ((In = fopen(dillorc, "r")) == NULL) {
+      DLIB_MSG("dGetenableunveil: unable to open dillorc.\n");
+      return (NULL);
+   }
+   while ((rcline = dGetline(In)) != NULL) {
+      if (strncmp(rcline, "enable_unveil", 13) == 0)
+         break;
+      dFree(rcline);
+   }
+   fclose(In);
+   if (!rcline) {
+      value = NULL;
+      DLIB_MSG("dGetenableunveil: no 'enable_unveil' in dillorc.\n");
+   } else {
+      len = (int) strlen(rcline);
+      if (len && rcline[len - 1] == '\n')
+         rcline[len - 1] = 0;
+      if ((p = strchr(rcline, '='))) {
+         while (*++p == ' ');
+         value = dStrdup(p);
+      } else {
+         value = NULL;
+	 DLIB_MSG("dGetenableunveil: error parsing value in dillorc.\n");
+      }
+   }
+   dFree(rcline);
+   return (value);
+}
+
+/**
+ * Use unveil on OpenBSD
+ */
+void *dUnveil(const char *path, const char *perm)
+{
+    #ifdef ENABLE_UNVEIL
+    #ifdef __OpenBSD__
+    int unveil(const char *path, const char *permissions);
+    if (unveil(path, perm) == -1) {
+       DLIB_MSG("unveil(%s, %s) failed: %s\n", path, perm, strerror(errno));
+       exit(1);
+    }
+    #endif
+    #endif
+}
+
+/**
  * Get a line from a FILE stream.
  * Return value: read line on success, NULL on EOF.
  */
diff -upr a/dlib/dlib.h b/dlib/dlib.h
--- a/dlib/dlib.h	Sun Aug 11 22:21:59 2024
+++ b/dlib/dlib.h	Tue Aug 20 19:08:02 2024
@@ -175,6 +175,9 @@ void dLib_show_messages(bool_t show);
  */
 char *dGetcwd(void);
 char *dGethomedir(void);
+char *dGetsavedir(void);
+char *dGetenableunveil(void);
+void *dUnveil(const char *path, const char *perm);
 char *dGetline(FILE *stream);
 int dClose(int fd);
 int dUsleep(unsigned long us);
diff -upr a/dpi/bookmarks.c b/dpi/bookmarks.c
--- a/dpi/bookmarks.c	Sun Aug 11 22:21:59 2024
+++ b/dpi/bookmarks.c	Tue Aug 20 19:08:02 2024
@@ -37,6 +37,7 @@
 #include <signal.h>
 #include "../dpip/dpip.h"
 #include "dpiutil.h"
+#include "../dlib/dlib.h"
 
 
 /*
@@ -1606,7 +1607,6 @@ static void termination_handler(int signum)
   exit(signum);
 }
 
-
 /*
  * -- MAIN -------------------------------------------------------------------
  */
@@ -1616,6 +1616,21 @@ int main(void) {
    socklen_t address_size;
    char *tok;
    Dsh *sh;
+
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         char *dil_bm = dStrconcat(dGethomedir(), "/.dillo/bm.txt", NULL);
+         dUnveil(dil_bm, "rwc");
+         dFree(dil_bm);
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+         dUnveil(dil_loc, "r");
+         dFree(dil_loc);
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
 
    /* Arrange the cleanup function for terminations via exit() */
    atexit(cleanup);
diff -upr a/dpi/cookies.c b/dpi/cookies.c
--- a/dpi/cookies.c	Sun Aug 11 22:21:59 2024
+++ b/dpi/cookies.c	Tue Aug 20 19:08:02 2024
@@ -50,6 +50,7 @@ int main(void)
 #include <signal.h>
 #include "dpiutil.h"
 #include "../dpip/dpip.h"
+#include "../dlib/dlib.h"
 
 
 /*
@@ -1632,7 +1633,6 @@ static void termination_handler(int signum)
   exit(signum);
 }
 
-
 /*
  * -- MAIN -------------------------------------------------------------------
  */
@@ -1643,7 +1643,22 @@ int main(void) {
    int sock_fd, code;
    char *buf;
    Dsh *sh;
-
+   
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         char *cookiesrc_loc = dStrconcat(dGethomedir(), "/.dillo/cookiesrc", NULL);
+         dUnveil(cookiesrc_loc, "rwc");
+         dFree(cookiesrc_loc);
+         char *cookies_loc = dStrconcat(dGethomedir(), "/.dillo/cookies.txt", NULL);
+         dUnveil(cookies_loc, "rwc");
+         dFree(cookies_loc);
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
+   
    /* Arrange the cleanup function for terminations via exit() */
    atexit(cleanup);
 
diff -upr a/dpi/datauri.c b/dpi/datauri.c
--- a/dpi/datauri.c	Sun Aug 11 22:21:59 2024
+++ b/dpi/datauri.c	Tue Aug 20 19:08:02 2024
@@ -21,6 +21,7 @@
 #include "../dpip/dpip.h"
 #include "dpiutil.h"
 #include "../src/misc.h"
+#include "../dlib/dlib.h"
 
 /*
  * Debugging macros
@@ -290,6 +291,19 @@ int main(void)
    unsigned char *data;
    int rc;
    size_t data_size = 0;
+   
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL	
+         dUnveil("/tmp", "rwc");
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo/dpid_comm_keys", NULL);
+         dUnveil(dil_loc, "rwc");
+         dFree(dil_loc);
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
 
    /* Initialize the SockHandler */
    sh = a_Dpip_dsh_new(STDIN_FILENO, STDOUT_FILENO, 8*1024);
diff -upr a/dpi/downloads.cc b/dpi/downloads.cc
--- a/dpi/downloads.cc	Sun Aug 11 22:21:59 2024
+++ b/dpi/downloads.cc	Tue Aug 20 19:08:13 2024
@@ -45,6 +45,7 @@
 #include "config.h"
 #include "dpiutil.h"
 #include "../dpip/dpip.h"
+#include "../dlib/dlib.h"
 
 /*
  * Debugging macros
@@ -206,7 +207,6 @@ static char *escape_tooltip(const char *buf, ssize_t l
    return ret;
 }
 
-
 /*
  * Global variables
  */
@@ -1098,13 +1098,37 @@ static void custLabelMeasure(const Fl_Label* o, int& W
    fl_measure(o->value, W, H, interpret_symbols);
 }
 
-
-
 //int main(int argc, char **argv)
 int main()
 {
    int ww = 420, wh = 85;
-
+   
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         dUnveil("/tmp", "rwc");
+         dUnveil("/etc/fonts", "r");
+         dUnveil("/usr/local/bin/wget", "x");
+         char *xauth_loc = dStrconcat(dGethomedir(), "/.Xauthority", NULL);
+         char *xauth = getenv("AUTHORITY");
+         if (xauth && strlen(xauth)) {
+            dUnveil(xauth, "r");
+            } else {
+                   dUnveil(xauth_loc, "r");
+		   } 
+         dFree(xauth_loc);
+         dFree(xauth); 
+         dUnveil("/usr/local/share/fonts", "r");
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+         dUnveil(dil_loc, "r");
+         dFree(dil_loc);
+         dUnveil(dGetsavedir(), "rw");
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
+   
    Fl::lock();
 
    // Disable '@' and '&' interpretation in normal labels.
diff -upr a/dpi/file.c b/dpi/file.c
--- a/dpi/file.c	Sun Aug 11 22:21:59 2024
+++ b/dpi/file.c	Tue Aug 20 19:08:02 2024
@@ -37,6 +37,7 @@
 #include "../dpip/dpip.h"
 #include "dpiutil.h"
 #include "d_size.h"
+#include "../dlib/dlib.h"
 
 /*
  * Debugging macros
@@ -1063,12 +1064,31 @@ static int File_check_fds(uint_t seconds)
    return st;
 }
 
-
 int main(void)
 {
    struct sockaddr_in sin;
    socklen_t sin_sz;
    int sock_fd, c_st, st = 1;
+
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         dUnveil(dGetsavedir(), "r");
+         dUnveil("/tmp", "rw");
+         char *home_loc = dStrconcat(dGethomedir(), "", NULL);
+         dUnveil(home_loc, "r");
+         dFree(home_loc);
+         char *ssh_loc = dStrconcat(dGethomedir(), "/.ssh", NULL);
+         dUnveil(ssh_loc, "");
+         dFree(ssh_loc);
+         char *config_loc = dStrconcat(dGethomedir(), "/.config", NULL);
+         dUnveil(config_loc, "");
+         dFree(config_loc);
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
 
    /* Arrange the cleanup function for abnormal terminations */
    if (signal (SIGINT, termination_handler) == SIG_IGN)
diff -upr a/dpi/ftp.c b/dpi/ftp.c
--- a/dpi/ftp.c	Sun Aug 11 22:21:59 2024
+++ b/dpi/ftp.c	Tue Aug 20 19:08:02 2024
@@ -44,6 +44,7 @@
 #include "../dpip/dpip.h"
 #include "dpiutil.h"
 #include "d_size.h"
+#include "../dlib/dlib.h"
 
 /*
  * Debugging macros
@@ -282,6 +283,21 @@ int main(int argc, char **argv)
    int st, rc;
    char *p, *d_cmd;
 
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         dUnveil("/tmp", "rwc");
+         dUnveil("/usr/local/bin/wget", "x");
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+         dUnveil(dil_loc, "r");
+         dFree(dil_loc);
+         dUnveil(dGetsavedir(), "rwc");
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
+   
    /* wget may need to write a temporary file... */
    rc = chdir("/tmp");
    if (rc == -1) {
diff -upr a/dpi/vsource.c b/dpi/vsource.c
--- a/dpi/vsource.c	Sun Aug 11 22:21:59 2024
+++ b/dpi/vsource.c	Tue Aug 20 19:08:02 2024
@@ -21,6 +21,7 @@
 #include <errno.h>
 #include "../dpip/dpip.h"
 #include "dpiutil.h"
+#include "../dlib/dlib.h"
 
 /*
  * Debugging macros
@@ -188,6 +189,18 @@ int main(void)
    char *dpip_tag, *cmd = NULL, *cmd2 = NULL, *url = NULL, *size_str = NULL;
    char *d_cmd;
 
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+         dUnveil(dil_loc, "r");
+         dFree(dil_loc);
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
+   
    _MSG("starting...\n");
    //sleep(20);
 
diff -upr a/dpid/main.c b/dpid/main.c
--- a/dpid/main.c	Sun Aug 11 22:21:59 2024
+++ b/dpid/main.c	Tue Aug 20 19:08:02 2024
@@ -236,6 +236,19 @@ int main(void)
    //daemon(0,0); /* Use 0,1 for feedback */
    /* TODO: call setsid() ?? */
 
+   /* Use unveil on OpenBSD */
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+         dUnveil("/usr/local/lib/dillo", "rx");
+         dUnveil("/usr/local/etc/dillo", "r");
+         char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+         dUnveil(dil_loc, "rwc");
+         dUnveil(NULL, NULL);
+         #endif
+      }
+   }
+   
    /* Allow read and write access, but only for the user.
     * TODO: can this cause trouble with umount? */
    umask(0077);
diff -upr a/src/dillo.cc b/src/dillo.cc
--- a/src/dillo.cc	Sun Aug 11 22:21:59 2024
+++ b/src/dillo.cc	Tue Aug 20 19:08:02 2024
@@ -463,7 +463,53 @@ int main(int argc, char **argv)
       fclose(fp);
    }
    dLib_show_messages(prefs.show_msg);
-
+   
+   // Use unveil
+   if (dGetenableunveil() != NULL) {
+      if (strncmp(dGetenableunveil(), "YES", 3) == 0) {
+         #ifdef ENABLE_UNVEIL
+	  const char *home = dGethomedir();
+          const char *save = prefs.save_dir;
+          int nsave = strlen(save);
+          int nhome = strlen(home);
+          if (nsave <= nhome) {
+             /* Prevent save_dir="/home" and save_dir=$HOME */
+             if (strncmp(save, home, nsave) == 0) {
+                MSG("save_dir cannot contain home\n");
+                exit(1);
+                }
+          }
+          dUnveil("/usr/local/share/fonts", "r");
+          dUnveil("/usr/local/share/icons", "r");
+          dUnveil("/usr/X11R6/share/X11/locale", "r");
+          dUnveil("/usr/X11R6/lib/X11/fonts", "r");
+          dUnveil("/usr/local/etc/dillo", "r");
+          dUnveil("/tmp", "rwc");
+          dUnveil("/usr/local/bin/dpid", "x");
+          dUnveil("/etc/fonts", "r");
+          dUnveil("/etc/resolv.conf", "r");
+          dUnveil("/etc/ssl/cert.pem", "r");
+          dUnveil(prefs.save_dir, "rwc");
+          char *dil_loc = dStrconcat(dGethomedir(), "/.dillo", NULL);
+          dUnveil(dil_loc, "rwc");
+          dFree(dil_loc);
+          char *icons_loc = dStrconcat(dGethomedir(), "/.icons", NULL);
+          dUnveil(icons_loc, "r");
+          dFree(icons_loc);
+          char *xauth_loc = dStrconcat(dGethomedir(), "/.Xauthority", NULL);
+          char *xauth = getenv("AUTHORITY");
+        	 if (xauth && strlen(xauth)) {
+                    dUnveil(xauth, "r");
+	            } else {
+                           dUnveil(xauth_loc, "r");
+		           } 
+          dFree(xauth_loc);
+          dFree(xauth); 
+          dUnveil(NULL, NULL);
+          #endif
+       } 
+    }
+    
    // initialize internal modules
    a_Dpi_init();
    a_Dns_init();
diff -upr a/src/prefs.c b/src/prefs.c
--- a/src/prefs.c	Sun Aug 11 22:21:59 2024
+++ b/src/prefs.c	Tue Aug 20 19:08:02 2024
@@ -72,6 +72,7 @@ void a_Prefs_init(void)
    prefs.http_strict_transport_security = TRUE;
    prefs.http_force_https = FALSE;
    prefs.http_user_agent = dStrdup(PREFS_HTTP_USER_AGENT);
+   prefs.enable_unveil = FALSE;
    prefs.limit_text_width = FALSE;
    prefs.adjust_min_width = TRUE;
    prefs.adjust_table_min_width = TRUE;
diff -upr a/src/prefs.h b/src/prefs.h
--- a/src/prefs.h	Sun Aug 11 22:21:59 2024
+++ b/src/prefs.h	Tue Aug 20 19:08:02 2024
@@ -100,6 +100,7 @@ typedef struct {
    bool_t http_persistent_conns;
    bool_t http_strict_transport_security;
    bool_t http_force_https;
+   bool_t enable_unveil;
    int32_t buffered_drawing;
    char *font_serif;
    char *font_sans_serif;
diff -upr a/src/prefsparser.cc b/src/prefsparser.cc
--- a/src/prefsparser.cc	Sun Aug 11 22:21:59 2024
+++ b/src/prefsparser.cc	Tue Aug 20 19:08:02 2024
@@ -182,6 +182,7 @@ void PrefsParser::parse(FILE *fp)
         PREFS_BOOL, 0 },
       { "http_force_https", &prefs.http_force_https, PREFS_BOOL, 0 },
       { "http_user_agent", &prefs.http_user_agent, PREFS_STRING, 0 },
+      { "enable_unveil", &prefs.enable_unveil, PREFS_BOOL, 0 },
       { "limit_text_width", &prefs.limit_text_width, PREFS_BOOL, 0 },
       { "adjust_min_width", &prefs.adjust_min_width, PREFS_BOOL, 0 },
       { "adjust_table_min_width", &prefs.adjust_table_min_width, PREFS_BOOL, 0 },
_______________________________________________
Dillo-dev mailing list -- dillo-dev@mailman3.com
To unsubscribe send an email to dillo-dev-le...@mailman3.com

Reply via email to