+
+/*
+ * Returns 1 on sucess, 0 on failure
+ */
+static int
+bpf_dtab_grow(int increment)
+{
+ struct bpf_d **new_dtab = NULL;
+
+ new_dtab = (struct bpf_d **)_MALLOC(sizeof(struct bpf_d *) * (bpf_dtab_size + increment), M_DEVBUF, M_WAIT);
+ if (new_dtab == NULL)
+ return 0;
+
+ if (bpf_dtab) {
+ struct bpf_d **old_dtab;
+
+ bcopy(bpf_dtab, new_dtab, sizeof(struct bpf_d *) * bpf_dtab_size);
+ /*
+ * replace must be atomic with respect to free do bpf_dtab
+ * is always valid.
+ */
+ old_dtab = bpf_dtab;
+ bpf_dtab = new_dtab;
+ _FREE(old_dtab, M_DEVBUF);
+ }
+ else bpf_dtab = new_dtab;
+
+ bzero(bpf_dtab + bpf_dtab_size, sizeof(struct bpf_d *) * increment);
+
+ bpf_dtab_size += increment;
+
+ return 1;
+}
+
+static struct bpf_d *
+bpf_make_dev_t(int maj)
+{
+ struct bpf_d *d;
+
+ if (nbpfilter >= bpf_dtab_size && bpf_dtab_grow(NBPFILTER) == 0)
+ return NULL;
+
+ d = (struct bpf_d *)_MALLOC(sizeof(struct bpf_d), M_DEVBUF, M_WAIT);
+ if (d != NULL) {
+ int i = nbpfilter++;
+
+ bzero(d, sizeof(struct bpf_d));
+ bpf_dtab[i] = d;
+ D_MARKFREE(bpf_dtab[i]);
+ /*bpf_devfs_token[i] = */devfs_make_node(makedev(maj, i),
+ DEVFS_CHAR, UID_ROOT, GID_WHEEL, 0600,
+ "bpf%d", i);
+ }
+ return d;
+}
+