- Change internal function bpf_jit_compile() to return allocated size of
the generated binary and remove page size limitation for userland. - Use contigmalloc(9)/contigfree(9) instead of malloc(9)/free(9) to make sure the generated binary aligns properly and make it physically contiguous.
This commit is contained in:
parent
366652f987
commit
ae4fdab8a8
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=199498
@ -53,7 +53,7 @@ __FBSDID("$FreeBSD$");
|
||||
|
||||
#include <amd64/amd64/bpf_jit_machdep.h>
|
||||
|
||||
bpf_filter_func bpf_jit_compile(struct bpf_insn *, u_int, int *);
|
||||
bpf_filter_func bpf_jit_compile(struct bpf_insn *, u_int, size_t *, int *);
|
||||
|
||||
/*
|
||||
* emit routine to update the jump table
|
||||
@ -97,7 +97,7 @@ emit_code(bpf_bin_stream *stream, u_int value, u_int len)
|
||||
* Function that does the real stuff
|
||||
*/
|
||||
bpf_filter_func
|
||||
bpf_jit_compile(struct bpf_insn *prog, u_int nins, int *mem)
|
||||
bpf_jit_compile(struct bpf_insn *prog, u_int nins, size_t *size, int *mem)
|
||||
{
|
||||
bpf_bin_stream stream;
|
||||
struct bpf_insn *ins;
|
||||
@ -481,23 +481,21 @@ bpf_jit_compile(struct bpf_insn *prog, u_int nins, int *mem)
|
||||
#ifndef _KERNEL
|
||||
if (mprotect(stream.ibuf, stream.cur_ip,
|
||||
PROT_READ | PROT_EXEC) != 0) {
|
||||
munmap(stream.ibuf, BPF_JIT_MAXSIZE);
|
||||
munmap(stream.ibuf, stream.cur_ip);
|
||||
stream.ibuf = NULL;
|
||||
}
|
||||
#endif
|
||||
*size = stream.cur_ip;
|
||||
break;
|
||||
}
|
||||
|
||||
#ifdef _KERNEL
|
||||
stream.ibuf = (char *)malloc(stream.cur_ip, M_BPFJIT, M_NOWAIT);
|
||||
stream.ibuf = (char *)contigmalloc(stream.cur_ip, M_BPFJIT,
|
||||
M_NOWAIT, 0, ~0ULL, 16, 0);
|
||||
if (stream.ibuf == NULL)
|
||||
break;
|
||||
#else
|
||||
if (stream.cur_ip > BPF_JIT_MAXSIZE) {
|
||||
stream.ibuf = NULL;
|
||||
break;
|
||||
}
|
||||
stream.ibuf = (char *)mmap(NULL, BPF_JIT_MAXSIZE,
|
||||
stream.ibuf = (char *)mmap(NULL, stream.cur_ip,
|
||||
PROT_READ | PROT_WRITE, MAP_ANON, -1, 0);
|
||||
if (stream.ibuf == MAP_FAILED) {
|
||||
stream.ibuf = NULL;
|
||||
|
@ -53,7 +53,7 @@ __FBSDID("$FreeBSD$");
|
||||
|
||||
#include <i386/i386/bpf_jit_machdep.h>
|
||||
|
||||
bpf_filter_func bpf_jit_compile(struct bpf_insn *, u_int, int *);
|
||||
bpf_filter_func bpf_jit_compile(struct bpf_insn *, u_int, size_t *, int *);
|
||||
|
||||
/*
|
||||
* emit routine to update the jump table
|
||||
@ -97,7 +97,7 @@ emit_code(bpf_bin_stream *stream, u_int value, u_int len)
|
||||
* Function that does the real stuff
|
||||
*/
|
||||
bpf_filter_func
|
||||
bpf_jit_compile(struct bpf_insn *prog, u_int nins, int *mem)
|
||||
bpf_jit_compile(struct bpf_insn *prog, u_int nins, size_t *size, int *mem)
|
||||
{
|
||||
bpf_bin_stream stream;
|
||||
struct bpf_insn *ins;
|
||||
@ -504,23 +504,21 @@ bpf_jit_compile(struct bpf_insn *prog, u_int nins, int *mem)
|
||||
#ifndef _KERNEL
|
||||
if (mprotect(stream.ibuf, stream.cur_ip,
|
||||
PROT_READ | PROT_EXEC) != 0) {
|
||||
munmap(stream.ibuf, BPF_JIT_MAXSIZE);
|
||||
munmap(stream.ibuf, stream.cur_ip);
|
||||
stream.ibuf = NULL;
|
||||
}
|
||||
#endif
|
||||
*size = stream.cur_ip;
|
||||
break;
|
||||
}
|
||||
|
||||
#ifdef _KERNEL
|
||||
stream.ibuf = (char *)malloc(stream.cur_ip, M_BPFJIT, M_NOWAIT);
|
||||
stream.ibuf = (char *)contigmalloc(stream.cur_ip, M_BPFJIT,
|
||||
M_NOWAIT, 0, ~0ULL, 16, 0);
|
||||
if (stream.ibuf == NULL)
|
||||
break;
|
||||
#else
|
||||
if (stream.cur_ip > BPF_JIT_MAXSIZE) {
|
||||
stream.ibuf = NULL;
|
||||
break;
|
||||
}
|
||||
stream.ibuf = (char *)mmap(NULL, BPF_JIT_MAXSIZE,
|
||||
stream.ibuf = (char *)mmap(NULL, stream.cur_ip,
|
||||
PROT_READ | PROT_WRITE, MAP_ANON, -1, 0);
|
||||
if (stream.ibuf == MAP_FAILED) {
|
||||
stream.ibuf = NULL;
|
||||
|
@ -51,7 +51,7 @@ __FBSDID("$FreeBSD$");
|
||||
#include <net/bpf.h>
|
||||
#include <net/bpf_jitter.h>
|
||||
|
||||
bpf_filter_func bpf_jit_compile(struct bpf_insn *, u_int, int *);
|
||||
bpf_filter_func bpf_jit_compile(struct bpf_insn *, u_int, size_t *, int *);
|
||||
|
||||
static u_int bpf_jit_accept_all(u_char *, u_int, u_int);
|
||||
|
||||
@ -81,7 +81,8 @@ bpf_jitter(struct bpf_insn *fp, int nins)
|
||||
}
|
||||
|
||||
/* Create the binary */
|
||||
if ((filter->func = bpf_jit_compile(fp, nins, filter->mem)) == NULL) {
|
||||
if ((filter->func = bpf_jit_compile(fp, nins, &filter->size,
|
||||
filter->mem)) == NULL) {
|
||||
free(filter, M_BPFJIT);
|
||||
return (NULL);
|
||||
}
|
||||
@ -94,7 +95,7 @@ bpf_destroy_jit_filter(bpf_jit_filter *filter)
|
||||
{
|
||||
|
||||
if (filter->func != bpf_jit_accept_all)
|
||||
free(filter->func, M_BPFJIT);
|
||||
contigfree(filter->func, filter->size, M_BPFJIT);
|
||||
free(filter, M_BPFJIT);
|
||||
}
|
||||
#else
|
||||
@ -116,7 +117,8 @@ bpf_jitter(struct bpf_insn *fp, int nins)
|
||||
}
|
||||
|
||||
/* Create the binary */
|
||||
if ((filter->func = bpf_jit_compile(fp, nins, filter->mem)) == NULL) {
|
||||
if ((filter->func = bpf_jit_compile(fp, nins, &filter->size,
|
||||
filter->mem)) == NULL) {
|
||||
free(filter);
|
||||
return (NULL);
|
||||
}
|
||||
@ -129,7 +131,7 @@ bpf_destroy_jit_filter(bpf_jit_filter *filter)
|
||||
{
|
||||
|
||||
if (filter->func != bpf_jit_accept_all)
|
||||
munmap(filter->func, BPF_JIT_MAXSIZE);
|
||||
munmap(filter->func, filter->size);
|
||||
free(filter);
|
||||
}
|
||||
#endif
|
||||
|
@ -36,8 +36,6 @@
|
||||
|
||||
#ifdef _KERNEL
|
||||
MALLOC_DECLARE(M_BPFJIT);
|
||||
#else
|
||||
#define BPF_JIT_MAXSIZE PAGE_SIZE
|
||||
#endif
|
||||
|
||||
extern int bpf_jitter_enable;
|
||||
@ -55,7 +53,7 @@ typedef u_int (*bpf_filter_func)(u_char *, u_int, u_int);
|
||||
typedef struct bpf_jit_filter {
|
||||
/* The native filtering binary, in the form of a bpf_filter_func. */
|
||||
bpf_filter_func func;
|
||||
|
||||
size_t size;
|
||||
int mem[BPF_MEMWORDS]; /* Scratch memory */
|
||||
} bpf_jit_filter;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user