From mboxrd@z Thu Jan 1 00:00:00 1970 From: Jakub Kicinski Subject: Re: Allow bpf_perf_event_output to access packet data Date: Mon, 10 Sep 2018 10:26:42 +0200 Message-ID: <20180910102642.7ea6da00@cakuba> References: Mime-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: 7bit Cc: netdev@vger.kernel.org To: Lorenz Bauer Return-path: Received: from mail-pg1-f181.google.com ([209.85.215.181]:38704 "EHLO mail-pg1-f181.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1727593AbeIJNTn (ORCPT ); Mon, 10 Sep 2018 09:19:43 -0400 Received: by mail-pg1-f181.google.com with SMTP id t84-v6so8241842pgb.5 for ; Mon, 10 Sep 2018 01:26:51 -0700 (PDT) In-Reply-To: Sender: netdev-owner@vger.kernel.org List-ID: On Fri, 7 Sep 2018 15:56:15 +0100, Lorenz Bauer wrote: > Hello list, > > I'm attempting to use bpf_perf_event_output to do packet sampling from XDP. > > The code basically runs before our other XDP code, does a > perf_event_output with the full packet (for now) and then tail calls > into DDoS mitigation, etc. > > I've just discovered that perf_event_output isn't allowed to access > packet data by the verifier. Is this something that could be allowed? Hi Lorenz! The amount of packet data to output is controlled by high bits of the "flags" parameter. This is a trivial sample: struct bpf_map_def SEC("maps") pa = { .type = BPF_MAP_TYPE_PERF_EVENT_ARRAY, .key_size = sizeof(int), .value_size = sizeof(int), .max_entries = 64, }; int xdp_prog1(struct xdp_md *xdp) { int key = 0; bpf_perf_event_output(xdp, &pa, 0x20ffffffffULL, &key, 0); return XDP_PASS; } The 0x20ffffffffULL will mean use the index in the map for current CPU (0xffffffff), and output 32 bytes of the context (0x20 << 32). For networking programs context means the packet (slightly confusingly). These are the relevant defines from bpf.h: /* BPF_FUNC_perf_event_output, BPF_FUNC_perf_event_read and * BPF_FUNC_perf_event_read_value flags. */ #define BPF_F_INDEX_MASK 0xffffffffULL #define BPF_F_CURRENT_CPU BPF_F_INDEX_MASK /* BPF_FUNC_perf_event_output for sk_buff input context. */ #define BPF_F_CTXLEN_MASK (0xfffffULL << 32) Also check out: bpftool map event_pipe id $ID For simple way to dump the events in user space.