Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

wip: set rodata (if any) #6

Open
wants to merge 5 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 1 addition & 3 deletions .devcontainer/Dockerfile
Original file line number Diff line number Diff line change
@@ -1,12 +1,10 @@
FROM docker.io/archlinux:latest

RUN pacman -Syy --noconfirm
RUN pacman -S --noconfirm nodejs clang llvm gcc linux-headers bpf unzip docker vi vim
RUN pacman -S --noconfirm nodejs clang llvm gcc linux-headers bpf unzip docker vi vim gdb tree

RUN pacman -S --noconfirm --needed git base-devel



# user setup
WORKDIR /tmp
RUN useradd -m -r -u 1000 vscode -s /bin/bash
Expand Down
8 changes: 8 additions & 0 deletions README.txt
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,14 @@ BUILD

xmake -b bpf

In case you want to compile in debug mode:

xmake f -m debug

You will be able to read from the trace_pipe the logs of the BPF programs
and you will obtain the logs of libbpf into the stderr only if you compile
in debug mode.

TEST

To run the test suite you can do this:
Expand Down
32 changes: 24 additions & 8 deletions api/api.$progname.h.in
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
#include "${PROGNAME}.skel.h"

int ${OPERATION}${PROGNAME}(struct config *conf, after_attach_fn_t cb, bpf_obj_fn_t obj_cb)
#define ${PROGNAME}_has_rodata ${PROGNAME_WITH_RODATA}

int ${OPERATION}${PROGNAME}(struct config *conf, after_attach_fn_t cb, const void* rodata)
{
int err;
char buf[100];
Expand All @@ -15,14 +17,28 @@ int ${OPERATION}${PROGNAME}(struct config *conf, after_attach_fn_t cb, bpf_obj_f
return 1;
}

if (obj_cb) {
err = obj_cb(obj);
if (err)
{
fprintf(stderr, "traffico: fail calling obj callback\n");
goto destroy_${PROGNAME};
}
// Set read-only data
#if ${PROGNAME}_has_rodata
struct bpf_map *m = bpf_object__find_map_by_name(obj->obj, ".rodata");
if (!m || !bpf_map__is_internal(m))
{
log_err(conf, "fail: finding the .rodata map\n");
return 1;
}
const char *m_name = bpf_map__name(m);
size_t m_size = bpf_map__value_size(m);
log_out(conf, "done: finding the %s map (size %d)\n", m_name, m_size);
err = bpf_map__set_initial_value(m, rodata, m_size);
if (err)
{
free(m);
log_err(conf, "fail: setting the %s map\n", m_name);
return 1;
}
log_out(conf, "done: setting the %s map\n", m_name);
#else
log_out(conf, "done: moving on: no .rodata map\n");
#endif

err = ${PROGNAME}_bpf__load(obj);
if (err)
Expand Down
14 changes: 5 additions & 9 deletions api/api.h.in
Original file line number Diff line number Diff line change
Expand Up @@ -31,11 +31,9 @@ struct config
FILE *out_stream;
};

typedef int (*bpf_obj_fn_t)(void *obj);

typedef int (*after_attach_fn_t)(struct bpf_tc_hook hook, struct bpf_tc_opts opts);

typedef int (*attach_fn_t)(struct config *conf, after_attach_fn_t cb, bpf_obj_fn_t obj_cb);
typedef int (*attach_fn_t)(struct config *conf, after_attach_fn_t cb, const void* rodata);

/// logging
int print_log(FILE *f, bool verbosity, bool prefix, const char *fmt, va_list argptr)
Expand Down Expand Up @@ -78,7 +76,7 @@ int exit_after_attach(struct bpf_tc_hook hook, struct bpf_tc_opts opts)
}

/// non-existing programs
int ${OPERATION}0(struct config *conf, after_attach_fn_t cb, bpf_obj_fn_t obj_cb)
int ${OPERATION}0(struct config *conf, after_attach_fn_t cb, const void *rodata)
{
return 1;
}
Expand All @@ -88,15 +86,13 @@ ${API}
/// dispatch
attach_fn_t attach_fn[NUM_PROGRAMS] = { ${PROGRAMS_OPS_AS_SYMBOLS} };

int attach(struct config *conf, after_attach_fn_t cb, bpf_obj_fn_t obj_cb)
int attach(struct config *conf, after_attach_fn_t cb, const void* rodata)
{
attach_fn_t fn = attach_fn[conf->program];
if (fn) {
return fn(conf, cb, obj_cb);
return fn(conf, cb, rodata);
}
return ${OPERATION}0(conf, cb, obj_cb);
return ${OPERATION}0(conf, cb, NULL);
}



#endif // TRAFFICO_API_H
6 changes: 3 additions & 3 deletions api/xmake.lua
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ includes("xmake/repos.lua")
add_rules("mode.release", "mode.debug")

-- target to generate API components for every BPF program
target("every.api")
target("every-api")
set_kind("headeronly")
includes("../bpf")
add_deps("bpf")
Expand All @@ -23,10 +23,10 @@ target("every.api")
-- target to generate the API
target("api")
set_kind("headeronly")
add_deps("every.api")
add_deps("every-api")
on_config(function(target)
import("xmake.modules.api", { rootdir = os.projectdir() })
api(target, "every.api", true)
api(target, "every-api", true)

import("actions.config.configfiles", { alias = "gen_configfiles", rootdir = os.programdir() })
gen_configfiles()
Expand Down
1 change: 0 additions & 1 deletion bpf/block_ip.bpf.c
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@

char LICENSE[] SEC("license") = "Dual BSD/GPL";

// TODO > make this easy to configure via config struct
const volatile __u32 input = 0; // address to block (host byte order)

SEC("tc")
Expand Down
3 changes: 1 addition & 2 deletions bpf/block_port.bpf.c
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,7 @@

char LICENSE[] SEC("license") = "Dual BSD/GPL";

// TODO > make this easy to configure via config struct
const volatile __u32 input = 0;
const volatile __u16 input = 0; // port to block

SEC("tc")
int block_port(struct __sk_buff *skb)
Expand Down
2 changes: 1 addition & 1 deletion bpf/block_private_ipv4.bpf.c
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ int block_private_ipv4(struct __sk_buff *skb)

struct iphdr *ip_header = data + l3_offset;
const int l4_offset = l3_offset + sizeof(*ip_header);

if (data + l4_offset > data_end)
{
bpf_printk("classifier: [iph] size lenght check hit: continue");
Expand Down
6 changes: 3 additions & 3 deletions bpf/xmake.lua
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ rule("bpf")
set_extensions(".bpf.c")
on_config(function (target)
assert(is_host("linux"), 'rule("bpf"): only supported on linux!')
local headerdir = path.join(target:autogendir(), "rules", "bpf")
local headerdir = path.join(target:autogendir())
if not os.isdir(headerdir) then
os.mkdir(headerdir)
end
Expand All @@ -21,8 +21,8 @@ rule("bpf")
bpftool = filecfg.bpftool
end

local headerfile = path.join(target:autogendir(), "rules", "bpf", (path.filename(sourcefile):gsub("%.bpf%.c", ".skel.h")))
local objectfile = path.join(target:autogendir(), "rules", "bpf", (path.filename(sourcefile):gsub("%.bpf%.c", ".bpf.o")))
local headerfile = path.join(target:autogendir(), (path.filename(sourcefile):gsub("%.bpf%.c", ".skel.h")))
local objectfile = path.join(target:autogendir(), (path.filename(sourcefile):gsub("%.bpf%.c", ".bpf.o")))
local targetarch
if target:is_arch("x86_64", "i386") then
targetarch = "__TARGET_ARCH_x86"
Expand Down
9 changes: 8 additions & 1 deletion traffico.c
Original file line number Diff line number Diff line change
Expand Up @@ -197,7 +197,11 @@ void sig_handler(int signo)

static int libbpf_print_fn(enum libbpf_print_level level, const char *format, va_list args)
{
#ifndef NDEBUG
return print_log(g_config.err_stream, level == LIBBPF_DEBUG && g_config.verbose, false, format, args);
#else
return 0;
#endif
}

int await(struct bpf_tc_hook hook, struct bpf_tc_opts opts)
Expand Down Expand Up @@ -240,5 +244,8 @@ int main(int argc, char **argv)

// Execute
log_info("prog: %s\n", g_programs_name[g_config.program]);
return attach(&g_config, &await, NULL);
__u32 input = 16843010;
__u8 *val = malloc(4);
memcpy(val, &input, 4); // memset(val, 1, 4);
return attach(&g_config, &await, val);
}
33 changes: 29 additions & 4 deletions xmake/modules/api.lua
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import("core.project.project")
import("lib.detect.check_cxsnippets")

-- get sourcefiles
function _get_programs(target_name)
Expand All @@ -17,6 +18,10 @@ function gen(target, source_target)
if not target then
raise("could not configure target")
end
local source_gendir = path.absolute(project.target(source_target):autogendir())
if not source_gendir then
raise("could not obtain the autogendir of the source target")
end

target:set("configdir", target:autogendir())

Expand All @@ -30,7 +35,22 @@ function gen(target, source_target)
local tempconf = path.join(os.tmpdir(), confname)
os.tryrm(tempconf)
os.cp(configfile_template_path, tempconf)
target:add("configfiles", tempconf, { variables = { PROGNAME = progname, OPERATION = "attach__" } })

local skelpath = path.join(source_gendir, progname .. ".skel.h")
local has_rodata = check_cxsnippets("void test() {&((struct " .. progname .. "_bpf*)0)->rodata;}", {includes = skelpath}) and 1 or 0
if has_rodata == 1 then
utils.dump(
check_cxsnippets('void test() {printf("%ld", sizeof(&((struct ' .. progname .. '_bpf*)0)->rodata));}', {includes = skelpath})
)
end

target:add("configfiles", tempconf, {
variables = {
PROGNAME = progname,
OPERATION = "attach__",
PROGNAME_WITH_RODATA = has_rodata
}
})
end
end

Expand All @@ -51,18 +71,23 @@ function main(target, components_target, banner)

local op = vars[1].variables.OPERATION
v["OPERATION"] = op


local descr = '" - '
local programs = {}
table.insert(programs, "0")
for _, v in ipairs(vars) do
for i, v in ipairs(vars) do
table.insert(programs, v.variables.PROGNAME)
descr = descr .. v.variables.PROGNAME .. (v.variables.PROGNAME_WITH_RODATA == 1 and ' [input]' or '')
if i ~= #vars then
descr = descr .. '\\n - '
end
end
table.sort(programs)
v["PROGRAMS_AS_SYMBOLS"] = 'program_' .. table.concat(programs, ", program_")
v["PROGRAMS_AS_STRINGS"] = '"' .. table.concat(programs, '", "') .. '"'
v["PROGRAMS_OPS_AS_SYMBOLS"] = op .. table.concat(programs, ', ' .. op)
table.remove(programs, 1)
v["PROGRAMS_DESCRIPTION"] = '" - ' .. table.concat(programs, '\\n - ') .. '"'
v["PROGRAMS_DESCRIPTION"] = descr .. '"'

local content = ""
for i, c in ipairs(components) do
Expand Down