Only the bits necessary to set up a filter and lock down an incoming interface.


Index: kern/kern_pledge.c
===================================================================
RCS file: /cvs/src/sys/kern/kern_pledge.c,v
retrieving revision 1.174
diff -u -p -r1.174 kern_pledge.c
--- kern/kern_pledge.c  3 Jul 2016 04:36:08 -0000       1.174
+++ kern/kern_pledge.c  5 Jul 2016 17:35:04 -0000
@@ -79,7 +79,7 @@
 #include "drm.h"
 #endif
 
-int pledgereq_flags(const char *req);
+uint64_t pledgereq_flags(const char *req);
 int canonpath(const char *input, char *buf, size_t bufsize);
 int substrcmp(const char *p1, size_t s1, const char *p2, size_t s2);
 int resolvpath(struct proc *p, char **rdir, size_t *rdirlen, char **cwd,
@@ -359,6 +359,7 @@ static const struct {
        uint64_t flags;
 } pledgereq[] = {
        { "audio",              PLEDGE_AUDIO },
+       { "bpf",                PLEDGE_BPF },
        { "chown",              PLEDGE_CHOWN | PLEDGE_CHOWNUID },
        { "cpath",              PLEDGE_CPATH },
        { "disklabel",          PLEDGE_DISKLABEL },
@@ -404,7 +405,7 @@ sys_pledge(struct proc *p, void *v, regi
        if (SCARG(uap, request)) {
                size_t rbuflen;
                char *rbuf, *rp, *pn;
-               int f;
+               uint64_t f;
 
                rbuf = malloc(MAXPATHLEN, M_TEMP, M_WAITOK);
                error = copyinstr(SCARG(uap, request), rbuf, MAXPATHLEN,
@@ -1198,6 +1199,25 @@ pledge_ioctl(struct proc *p, long com, s
 #endif /* NAUDIO > 0 */
        }
 
+       if ((p->p_p->ps_pledge & PLEDGE_BPF)) {
+               switch (com) {
+               case BIOCGBLEN:
+               case BIOCVERSION:
+               case BIOCIMMEDIATE:
+               case BIOCSFILDROP:
+               case BIOCSHDRCMPLT:
+               case BIOCSETF:
+               case BIOCSETIF:
+               case BIOCSETWF:
+               case BIOCLOCK:
+                       if ((fp->f_type == DTYPE_VNODE) &&
+                           (vp->v_type == VCHR) &&
+                           (cdevsw[major(vp->v_rdev)].d_open == bpfopen))
+                               return (0);
+                       break;
+               }
+       }
+
        if ((p->p_p->ps_pledge & PLEDGE_DISKLABEL)) {
                switch (com) {
                case DIOCGDINFO:
@@ -1514,7 +1534,7 @@ pledge_swapctl(struct proc *p)
 }
 
 /* bsearch over pledgereq. return flags value if found, 0 else */
-int
+uint64_t
 pledgereq_flags(const char *req_name)
 {
        int base = 0, cmp, i, lim;
Index: sys/pledge.h
===================================================================
RCS file: /cvs/src/sys/sys/pledge.h,v
retrieving revision 1.29
diff -u -p -r1.29 pledge.h
--- sys/pledge.h        3 Jul 2016 04:36:08 -0000       1.29
+++ sys/pledge.h        5 Jul 2016 17:35:04 -0000
@@ -58,6 +58,7 @@
 #define PLEDGE_VMM     0x0000000040000000ULL   /* vmm ioctls */
 #define PLEDGE_CHOWN   0x0000000080000000ULL   /* chown(2) family */
 #define PLEDGE_CHOWNUID        0x0000000100000000ULL   /* allow owner/group 
changes */
+#define PLEDGE_BPF     0x0000000200000000ULL   /* bpf ioctls */
 
 /*
  * Bits outside PLEDGE_USERSET are used by the kernel itself
@@ -103,6 +104,7 @@ static struct {
        { PLEDGE_DRM,           "drm" },
        { PLEDGE_VMM,           "vmm" },
        { PLEDGE_CHOWNUID,      "chown" },
+       { PLEDGE_BPF,           "bpf" },
        { 0, NULL },
 };
 #endif

Reply via email to