162306a36Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0 262306a36Sopenharmony_ci/* eBPF example program: 362306a36Sopenharmony_ci * 462306a36Sopenharmony_ci * - Loads eBPF program 562306a36Sopenharmony_ci * 662306a36Sopenharmony_ci * The eBPF program loads a filter from file and attaches the 762306a36Sopenharmony_ci * program to a cgroup using BPF_PROG_ATTACH 862306a36Sopenharmony_ci */ 962306a36Sopenharmony_ci 1062306a36Sopenharmony_ci#define _GNU_SOURCE 1162306a36Sopenharmony_ci 1262306a36Sopenharmony_ci#include <stdio.h> 1362306a36Sopenharmony_ci#include <stdlib.h> 1462306a36Sopenharmony_ci#include <stddef.h> 1562306a36Sopenharmony_ci#include <string.h> 1662306a36Sopenharmony_ci#include <unistd.h> 1762306a36Sopenharmony_ci#include <assert.h> 1862306a36Sopenharmony_ci#include <errno.h> 1962306a36Sopenharmony_ci#include <fcntl.h> 2062306a36Sopenharmony_ci#include <net/if.h> 2162306a36Sopenharmony_ci#include <linux/bpf.h> 2262306a36Sopenharmony_ci#include <bpf/bpf.h> 2362306a36Sopenharmony_ci#include <bpf/libbpf.h> 2462306a36Sopenharmony_ci 2562306a36Sopenharmony_ci#include "bpf_insn.h" 2662306a36Sopenharmony_ci 2762306a36Sopenharmony_cistatic int usage(const char *argv0) 2862306a36Sopenharmony_ci{ 2962306a36Sopenharmony_ci printf("Usage: %s cg-path filter-path [filter-id]\n", argv0); 3062306a36Sopenharmony_ci return EXIT_FAILURE; 3162306a36Sopenharmony_ci} 3262306a36Sopenharmony_ci 3362306a36Sopenharmony_ciint main(int argc, char **argv) 3462306a36Sopenharmony_ci{ 3562306a36Sopenharmony_ci int cg_fd, err, ret = EXIT_FAILURE, filter_id = 0, prog_cnt = 0; 3662306a36Sopenharmony_ci const char *link_pin_path = "/sys/fs/bpf/test_cgrp2_sock2"; 3762306a36Sopenharmony_ci struct bpf_link *link = NULL; 3862306a36Sopenharmony_ci struct bpf_program *progs[2]; 3962306a36Sopenharmony_ci struct bpf_program *prog; 4062306a36Sopenharmony_ci struct bpf_object *obj; 4162306a36Sopenharmony_ci 4262306a36Sopenharmony_ci if (argc < 3) 4362306a36Sopenharmony_ci return usage(argv[0]); 4462306a36Sopenharmony_ci 4562306a36Sopenharmony_ci if (argc > 3) 4662306a36Sopenharmony_ci filter_id = atoi(argv[3]); 4762306a36Sopenharmony_ci 4862306a36Sopenharmony_ci cg_fd = open(argv[1], O_DIRECTORY | O_RDONLY); 4962306a36Sopenharmony_ci if (cg_fd < 0) { 5062306a36Sopenharmony_ci printf("Failed to open cgroup path: '%s'\n", strerror(errno)); 5162306a36Sopenharmony_ci return ret; 5262306a36Sopenharmony_ci } 5362306a36Sopenharmony_ci 5462306a36Sopenharmony_ci obj = bpf_object__open_file(argv[2], NULL); 5562306a36Sopenharmony_ci if (libbpf_get_error(obj)) { 5662306a36Sopenharmony_ci printf("ERROR: opening BPF object file failed\n"); 5762306a36Sopenharmony_ci return ret; 5862306a36Sopenharmony_ci } 5962306a36Sopenharmony_ci 6062306a36Sopenharmony_ci bpf_object__for_each_program(prog, obj) { 6162306a36Sopenharmony_ci progs[prog_cnt] = prog; 6262306a36Sopenharmony_ci prog_cnt++; 6362306a36Sopenharmony_ci } 6462306a36Sopenharmony_ci 6562306a36Sopenharmony_ci if (filter_id >= prog_cnt) { 6662306a36Sopenharmony_ci printf("Invalid program id; program not found in file\n"); 6762306a36Sopenharmony_ci goto cleanup; 6862306a36Sopenharmony_ci } 6962306a36Sopenharmony_ci 7062306a36Sopenharmony_ci /* load BPF program */ 7162306a36Sopenharmony_ci if (bpf_object__load(obj)) { 7262306a36Sopenharmony_ci printf("ERROR: loading BPF object file failed\n"); 7362306a36Sopenharmony_ci goto cleanup; 7462306a36Sopenharmony_ci } 7562306a36Sopenharmony_ci 7662306a36Sopenharmony_ci link = bpf_program__attach_cgroup(progs[filter_id], cg_fd); 7762306a36Sopenharmony_ci if (libbpf_get_error(link)) { 7862306a36Sopenharmony_ci printf("ERROR: bpf_program__attach failed\n"); 7962306a36Sopenharmony_ci link = NULL; 8062306a36Sopenharmony_ci goto cleanup; 8162306a36Sopenharmony_ci } 8262306a36Sopenharmony_ci 8362306a36Sopenharmony_ci err = bpf_link__pin(link, link_pin_path); 8462306a36Sopenharmony_ci if (err < 0) { 8562306a36Sopenharmony_ci printf("ERROR: bpf_link__pin failed: %d\n", err); 8662306a36Sopenharmony_ci goto cleanup; 8762306a36Sopenharmony_ci } 8862306a36Sopenharmony_ci 8962306a36Sopenharmony_ci ret = EXIT_SUCCESS; 9062306a36Sopenharmony_ci 9162306a36Sopenharmony_cicleanup: 9262306a36Sopenharmony_ci bpf_link__destroy(link); 9362306a36Sopenharmony_ci bpf_object__close(obj); 9462306a36Sopenharmony_ci return ret; 9562306a36Sopenharmony_ci} 96