From patchwork Fri May 28 23:52:36 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kumar Kartikeya Dwivedi X-Patchwork-Id: 449867 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-15.7 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI, SPF_HELO_NONE, SPF_PASS, USER_AGENT_GIT autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 5DFBCC4708F for ; Fri, 28 May 2021 23:53:45 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 385C96135F for ; Fri, 28 May 2021 23:53:45 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229500AbhE1XzQ (ORCPT ); Fri, 28 May 2021 19:55:16 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:45338 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229594AbhE1XzP (ORCPT ); Fri, 28 May 2021 19:55:15 -0400 Received: from mail-pf1-x443.google.com (mail-pf1-x443.google.com [IPv6:2607:f8b0:4864:20::443]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 069A3C061574; Fri, 28 May 2021 16:53:40 -0700 (PDT) Received: by mail-pf1-x443.google.com with SMTP id z26so408654pfj.5; Fri, 28 May 2021 16:53:40 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=/Agy9x6Mg8As0SqD+0oLSEwC0oEqk9fEZ+8467L6XkQ=; b=HY9k/UkijCOBkH3ui67wovUSEgGGVINUOmjrom8ZbKCTMwsc6ww/XaaexcXLikqtdJ 4AKi3RCpqpkgi8Babb/WClnTqNVZ9Sn3mdtwrsU8PhDYUHYEviwawY5nLIQKbk8bt5/f UemAoEDFNxai8LAJeduJRCb187SWQOTzMOy/NpIN8R9OdN2ZOVbTlhWNsFzLTLGoP1YZ sBfbmBa+FXXMnwqabILcDQQmY77tWh9SVlLmFCjLH9uwuhosTqnOSD2EtZ89GggRFDd+ aCzw0WBOM1GSIVKtri+zDhjwdSnwU/Stc8H42Dt+bREMNydiHwCUTdzYGhvFs8OpsBMo eCaA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=/Agy9x6Mg8As0SqD+0oLSEwC0oEqk9fEZ+8467L6XkQ=; b=f2Xw1EIqc7IO26I26nISd/v45YAeWGhZJXnd9Wx8CLgx+dSk6V2+ooSufHZny9Ghdu oCW/QU61ZBulHnYYD3z0EsBaGt0NojJDaUAdMgL5LRHTo8H6qDDHMpPFnpeSfRjrjejh RnAiJzbJNl8avmc7iONgVdKk2iPXHU5AtUcXhSTdvFvyhZEU6zoY6SgcnL6Juevb0X8J n2ygLJQ6hIAOtSMLiIjr8ofDX5VXBpmg6Tiwy57RSbM18fZ8AId9+TGhscdbz/NFANfs GPmtK5kn76RIxyHLP7sx4R7CFfgVLkAqsTVi1OTIxUlpRrR/8vluRyNURis+mTcOtSa2 r4Fw== X-Gm-Message-State: AOAM533nQ4/9fXaPpMce2s6NF/xFaicmxTy2O2sfCARbWTYL/mqcgG4o wNKhHg46bgOR0/bO6LVkXpkYvxTQ8Yw= X-Google-Smtp-Source: ABdhPJyjX4Hk/LGUFfPGemqT8kCp5nhpWS/6dbFDFf1MEyMalxl9iigVsR60g88pzPWWjMHl1lQAjA== X-Received: by 2002:a62:a101:0:b029:2e8:e878:bdc0 with SMTP id b1-20020a62a1010000b02902e8e878bdc0mr6227257pff.38.1622246019349; Fri, 28 May 2021 16:53:39 -0700 (PDT) Received: from localhost ([2402:3a80:11db:3aa9:ad24:a4a2:844f:6a0a]) by smtp.gmail.com with ESMTPSA id o6sm5304430pfb.126.2021.05.28.16.53.38 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 28 May 2021 16:53:39 -0700 (PDT) From: Kumar Kartikeya Dwivedi To: bpf@vger.kernel.org Cc: Kumar Kartikeya Dwivedi , Alexei Starovoitov , Daniel Borkmann , Andrii Nakryiko , Martin KaFai Lau , Song Liu , Yonghong Song , John Fastabend , KP Singh , "David S. Miller" , Jakub Kicinski , Jesper Dangaard Brouer , =?utf-8?q?Toke_H=C3=B8iland-J=C3=B8rgensen?= , netdev@vger.kernel.org Subject: [PATCH RFC bpf-next 01/15] samples: bpf: fix a couple of NULL dereferences Date: Sat, 29 May 2021 05:22:36 +0530 Message-Id: <20210528235250.2635167-2-memxor@gmail.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20210528235250.2635167-1-memxor@gmail.com> References: <20210528235250.2635167-1-memxor@gmail.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org When giving it just one ifname instead of two, it accesses argv[optind + 1], which is out of bounds (as argc < optind + 1). Signed-off-by: Kumar Kartikeya Dwivedi --- samples/bpf/xdp_redirect_map_user.c | 4 ++-- samples/bpf/xdp_redirect_user.c | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/samples/bpf/xdp_redirect_map_user.c b/samples/bpf/xdp_redirect_map_user.c index 0e8192688dfc..ad3cdc4c07d3 100644 --- a/samples/bpf/xdp_redirect_map_user.c +++ b/samples/bpf/xdp_redirect_map_user.c @@ -169,8 +169,8 @@ int main(int argc, char **argv) return 1; } - if (optind == argc) { - printf("usage: %s _IN _OUT\n", argv[0]); + if (argc <= optind + 1) { + usage(basename(argv[0])); return 1; } diff --git a/samples/bpf/xdp_redirect_user.c b/samples/bpf/xdp_redirect_user.c index 41d705c3a1f7..4e310660632b 100644 --- a/samples/bpf/xdp_redirect_user.c +++ b/samples/bpf/xdp_redirect_user.c @@ -130,8 +130,8 @@ int main(int argc, char **argv) if (!(xdp_flags & XDP_FLAGS_SKB_MODE)) xdp_flags |= XDP_FLAGS_DRV_MODE; - if (optind == argc) { - printf("usage: %s _IN _OUT\n", argv[0]); + if (argc <= optind + 1) { + usage(basename(argv[0])); return 1; } From patchwork Fri May 28 23:52:38 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kumar Kartikeya Dwivedi X-Patchwork-Id: 449866 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-15.7 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id CD447C4708C for ; Fri, 28 May 2021 23:53:49 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id A4031613F1 for ; Fri, 28 May 2021 23:53:49 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229663AbhE1XzX (ORCPT ); Fri, 28 May 2021 19:55:23 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:45372 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229647AbhE1XzW (ORCPT ); Fri, 28 May 2021 19:55:22 -0400 Received: from mail-pf1-x444.google.com (mail-pf1-x444.google.com [IPv6:2607:f8b0:4864:20::444]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id E200FC061574; Fri, 28 May 2021 16:53:46 -0700 (PDT) Received: by mail-pf1-x444.google.com with SMTP id y202so4413747pfc.6; Fri, 28 May 2021 16:53:46 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=V86Ql8jRAGbtURMVGsSlMfJC5php4p6tg5O5Rdj4NKQ=; b=pwcPA+yr8DFpkZnV3Jpk/aFTrind6HeRc1oAmrApBtCe1S2fCKHewqnIDFEwke/JUY R4fmxM+OKydOs9FOd3TKvZLS8WzNgdIj8Dw5mxnQF3ufPS2lAAWc4vNxHcEiuVcE/sg/ eSWkd104++t8SpxecSzodBJfuRmxPBRm86DS4Nw9a5A+JUkFBkLM69YGsiZcHJxCDpX1 BDGXDrnvs72h5uMaj6IZS81KoafZEaVpScbIv2fahfeFN0KXs29HAOkP0JILX4bq1ZP4 dJFBdH5bf75FubBJnvRrv0R8lmYilUGNfbPdIT4bgjnbApZBpCtDFfxcCtxNfUZROYo9 NEVA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=V86Ql8jRAGbtURMVGsSlMfJC5php4p6tg5O5Rdj4NKQ=; b=EVRm9q1y0xZQMEd0vyQbSyYCFy8TYluWueR9cFxwYyYJx9cEQT5mM0fS/PTQFsWiv3 a46MLzF9CEXilxrabcP4xdksfAORru1dycfoqMvjCafGkmMQeo7rNVWT+Rj5K4cIsTEu Hf2C7McKijwPN2S5t0KsOayCEkbmLyTCcXtx43pVP2AS+11/MKfGSmyrDDgrvjLemzP1 gVHolSW5M5b1vzUio651A9JRgigakOxeRla/tDfURyqu2e6nxT6qP4yAyFsF8E5p/DGk 5ZG9QMikl0pI9pmh5eK0QXaPvsvcOlC8QmQQlCQ4uSOgIja5EPUmlga8kBN3c+0wfssP G/BA== X-Gm-Message-State: AOAM531mHXInDlRZ4exCG8phY0L2G8e0o8RqPnEGcC4VvyDxokr1VhmQ bmbVRdI2pozaVrydNC4omgCW2D7yCqo= X-Google-Smtp-Source: ABdhPJyb+GcZNHkIqE/azlo0NNh7bNlCdqYJ4o4eufOxMvJ+YSqfQs+FYZKJfvc5HoDEuyyvu05z9Q== X-Received: by 2002:a62:1481:0:b029:2c1:1e90:c54 with SMTP id 123-20020a6214810000b02902c11e900c54mr6168441pfu.55.1622246026196; Fri, 28 May 2021 16:53:46 -0700 (PDT) Received: from localhost ([2402:3a80:11db:3aa9:ad24:a4a2:844f:6a0a]) by smtp.gmail.com with ESMTPSA id x125sm1191860pfx.201.2021.05.28.16.53.45 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 28 May 2021 16:53:45 -0700 (PDT) From: Kumar Kartikeya Dwivedi To: bpf@vger.kernel.org Cc: Kumar Kartikeya Dwivedi , Alexei Starovoitov , Daniel Borkmann , Andrii Nakryiko , Martin KaFai Lau , Song Liu , Yonghong Song , John Fastabend , KP Singh , "David S. Miller" , Jakub Kicinski , Jesper Dangaard Brouer , =?utf-8?q?Toke_H=C3=B8iland-J=C3=B8rgensen?= , netdev@vger.kernel.org Subject: [PATCH RFC bpf-next 03/15] samples: bpf: split out common bpf progs to its own file Date: Sat, 29 May 2021 05:22:38 +0530 Message-Id: <20210528235250.2635167-4-memxor@gmail.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20210528235250.2635167-1-memxor@gmail.com> References: <20210528235250.2635167-1-memxor@gmail.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org This is done to later reuse these in a way that can be shared among multiple samples. We are using xdp_redirect_cpu_kern.c as a base to build further support on top (mostly adding a few other things missing that xdp_monitor does in subsequent patches). Signed-off-by: Kumar Kartikeya Dwivedi --- samples/bpf/xdp_sample_kern.h | 220 ++++++++++++++++++++++++++++++++++ 1 file changed, 220 insertions(+) create mode 100644 samples/bpf/xdp_sample_kern.h diff --git a/samples/bpf/xdp_sample_kern.h b/samples/bpf/xdp_sample_kern.h new file mode 100644 index 000000000000..bb809542ac20 --- /dev/null +++ b/samples/bpf/xdp_sample_kern.h @@ -0,0 +1,220 @@ +// SPDX-License-Identifier: GPL-2.0 +/* GPLv2, Copyright(c) 2017 Jesper Dangaard Brouer, Red Hat, Inc. */ +#pragma once + +#include +#include + +#define MAX_CPUS 64 + +/* Common stats data record to keep userspace more simple */ +struct datarec { + __u64 processed; + __u64 dropped; + __u64 issue; + __u64 xdp_pass; + __u64 xdp_drop; + __u64 xdp_redirect; +}; + +/* Count RX packets, as XDP bpf_prog doesn't get direct TX-success + * feedback. Redirect TX errors can be caught via a tracepoint. + */ +struct { + __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); + __type(key, u32); + __type(value, struct datarec); + __uint(max_entries, 1); +} rx_cnt SEC(".maps"); + +/* Used by trace point */ +struct { + __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); + __type(key, u32); + __type(value, struct datarec); + __uint(max_entries, 2); + /* TODO: have entries for all possible errno's */ +} redirect_err_cnt SEC(".maps"); + +/* Used by trace point */ +struct { + __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); + __type(key, u32); + __type(value, struct datarec); + __uint(max_entries, MAX_CPUS); +} cpumap_enqueue_cnt SEC(".maps"); + +/* Used by trace point */ +struct { + __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); + __type(key, u32); + __type(value, struct datarec); + __uint(max_entries, 1); +} cpumap_kthread_cnt SEC(".maps"); + +/* Used by trace point */ +struct { + __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); + __type(key, u32); + __type(value, struct datarec); + __uint(max_entries, 1); +} exception_cnt SEC(".maps"); + +/*** Trace point code ***/ + +/* Tracepoint format: /sys/kernel/debug/tracing/events/xdp/xdp_redirect/format + * Code in: kernel/include/trace/events/xdp.h + */ +struct xdp_redirect_ctx { + u64 __pad; // First 8 bytes are not accessible by bpf code + int prog_id; // offset:8; size:4; signed:1; + u32 act; // offset:12 size:4; signed:0; + int ifindex; // offset:16 size:4; signed:1; + int err; // offset:20 size:4; signed:1; + int to_ifindex; // offset:24 size:4; signed:1; + u32 map_id; // offset:28 size:4; signed:0; + int map_index; // offset:32 size:4; signed:1; +}; // offset:36 + +enum { + XDP_REDIRECT_SUCCESS = 0, + XDP_REDIRECT_ERROR = 1 +}; + +static __always_inline +int xdp_redirect_collect_stat(struct xdp_redirect_ctx *ctx) +{ + u32 key = XDP_REDIRECT_ERROR; + struct datarec *rec; + int err = ctx->err; + + if (!err) + key = XDP_REDIRECT_SUCCESS; + + rec = bpf_map_lookup_elem(&redirect_err_cnt, &key); + if (!rec) + return 0; + rec->dropped += 1; + + return 0; /* Indicate event was filtered (no further processing)*/ + /* + * Returning 1 here would allow e.g. a perf-record tracepoint + * to see and record these events, but it doesn't work well + * in-practice as stopping perf-record also unload this + * bpf_prog. Plus, there is additional overhead of doing so. + */ +} + +SEC("tracepoint/xdp/xdp_redirect_err") +int trace_xdp_redirect_err(struct xdp_redirect_ctx *ctx) +{ + return xdp_redirect_collect_stat(ctx); +} + +SEC("tracepoint/xdp/xdp_redirect_map_err") +int trace_xdp_redirect_map_err(struct xdp_redirect_ctx *ctx) +{ + return xdp_redirect_collect_stat(ctx); +} + +/* Tracepoint format: /sys/kernel/debug/tracing/events/xdp/xdp_exception/format + * Code in: kernel/include/trace/events/xdp.h + */ +struct xdp_exception_ctx { + u64 __pad; // First 8 bytes are not accessible by bpf code + int prog_id; // offset:8; size:4; signed:1; + u32 act; // offset:12; size:4; signed:0; + int ifindex; // offset:16; size:4; signed:1; +}; + +SEC("tracepoint/xdp/xdp_exception") +int trace_xdp_exception(struct xdp_exception_ctx *ctx) +{ + struct datarec *rec; + u32 key = 0; + + rec = bpf_map_lookup_elem(&exception_cnt, &key); + if (!rec) + return 1; + rec->dropped += 1; + + return 0; +} + +/* Tracepoint: /sys/kernel/debug/tracing/events/xdp/xdp_cpumap_enqueue/format + * Code in: kernel/include/trace/events/xdp.h + */ +struct cpumap_enqueue_ctx { + u64 __pad; // First 8 bytes are not accessible by bpf code + int map_id; // offset:8; size:4; signed:1; + u32 act; // offset:12; size:4; signed:0; + int cpu; // offset:16; size:4; signed:1; + unsigned int drops; // offset:20; size:4; signed:0; + unsigned int processed; // offset:24; size:4; signed:0; + int to_cpu; // offset:28; size:4; signed:1; +}; + +SEC("tracepoint/xdp/xdp_cpumap_enqueue") +int trace_xdp_cpumap_enqueue(struct cpumap_enqueue_ctx *ctx) +{ + u32 to_cpu = ctx->to_cpu; + struct datarec *rec; + + if (to_cpu >= MAX_CPUS) + return 1; + + rec = bpf_map_lookup_elem(&cpumap_enqueue_cnt, &to_cpu); + if (!rec) + return 0; + rec->processed += ctx->processed; + rec->dropped += ctx->drops; + + /* Record bulk events, then userspace can calc average bulk size */ + if (ctx->processed > 0) + rec->issue += 1; + + /* Inception: It's possible to detect overload situations, via + * this tracepoint. This can be used for creating a feedback + * loop to XDP, which can take appropriate actions to mitigate + * this overload situation. + */ + return 0; +} + +/* Tracepoint: /sys/kernel/debug/tracing/events/xdp/xdp_cpumap_kthread/format + * Code in: kernel/include/trace/events/xdp.h + */ +struct cpumap_kthread_ctx { + u64 __pad; // First 8 bytes are not accessible + int map_id; // offset:8; size:4; signed:1; + u32 act; // offset:12; size:4; signed:0; + int cpu; // offset:16; size:4; signed:1; + unsigned int drops; // offset:20; size:4; signed:0; + unsigned int processed; // offset:24; size:4; signed:0; + int sched; // offset:28; size:4; signed:1; + unsigned int xdp_pass; // offset:32; size:4; signed:0; + unsigned int xdp_drop; // offset:36; size:4; signed:0; + unsigned int xdp_redirect; // offset:40; size:4; signed:0; +}; + +SEC("tracepoint/xdp/xdp_cpumap_kthread") +int trace_xdp_cpumap_kthread(struct cpumap_kthread_ctx *ctx) +{ + struct datarec *rec; + u32 key = 0; + + rec = bpf_map_lookup_elem(&cpumap_kthread_cnt, &key); + if (!rec) + return 0; + rec->processed += ctx->processed; + rec->dropped += ctx->drops; + rec->xdp_pass += ctx->xdp_pass; + rec->xdp_drop += ctx->xdp_drop; + rec->xdp_redirect += ctx->xdp_redirect; + + /* Count times kthread yielded CPU via schedule call */ + if (ctx->sched) + rec->issue++; + + return 0; +} From patchwork Fri May 28 23:52:40 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kumar Kartikeya Dwivedi X-Patchwork-Id: 449865 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-12.9 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,UNWANTED_LANGUAGE_BODY, USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id C7155C47087 for ; Fri, 28 May 2021 23:54:01 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id ADCCE608FC for ; Fri, 28 May 2021 23:54:01 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229707AbhE1Xze (ORCPT ); Fri, 28 May 2021 19:55:34 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:45400 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229693AbhE1Xza (ORCPT ); Fri, 28 May 2021 19:55:30 -0400 Received: from mail-pg1-x542.google.com (mail-pg1-x542.google.com [IPv6:2607:f8b0:4864:20::542]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 5BBF0C061574; Fri, 28 May 2021 16:53:54 -0700 (PDT) Received: by mail-pg1-x542.google.com with SMTP id j12so3699035pgh.7; Fri, 28 May 2021 16:53:54 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=eo+mNprptPl7srpNm0OMmFfBSNsoaoCtntagOadHIHQ=; b=Z0PPNl2UeIx7fncayz/zJQk3p5eqzRoCGOzlwi4NTJWgsUjcU6ftgwVA7eBNsVnGpZ icMjeveAq/k1ZNaZRod0N+EkGwnWA/UrD3zF0r5incCQfj1rNnbwXKz4/tObSutVOmw+ M+vrgdOJ+jx/KSQBa8+kb+TeqQQ8ErTHedifVVhcgbGD9lLD8NBcE1zD7cr6Hu/WCgff A/ZLUz9a0/0jkJqVdkFo/FA+IIhn57w0YfqtiBjq2uGwDllODmOmGLOgY4iACI6eHRhi lMJsZz6Mw6Eq5AqClgNt1uANaV5ZtBVoOyd8O+tFDEv7P9IDOdHqe0EfYXvjnze6WUwz NHRA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=eo+mNprptPl7srpNm0OMmFfBSNsoaoCtntagOadHIHQ=; b=cYkN5ds5LlFFVG5YGAQywZugN0mtgLl2UhUYoO085HpZBzMFxJqtyOwveG5XNmi2/D ptPkPAs2H+RZ/Swd07vzVPstRU0dc9EisCsTVNXzue4MnDJcEWuSSH9Mmp/aCGU2OgGn Aps0sCb29C5saeIwVYWk7sAMzxOmvDwFD9vc9cvNp8CTKEBbSmJSzraCayEPC5yWWwBw oqgGpEmNI4G72nHVh4E/4L7TmUz56JQRDm+PhuaXvGzIqHktsybRSEylG4x8M7jy42Mu E0qKFC+cVAYCiLSal7gjWRtLz08jllnmt7k3y1MWvODLUINIf+S9JozaaYeEq+Q6AfjF S1aw== X-Gm-Message-State: AOAM5313FKSfpiiUVrwlXnGf1whAqWAQgjgR/Bje2zN2DfX/Gr8LdQ+5 YDkEyzZslEqhzm+zg3bi9tTi+5vTmkA= X-Google-Smtp-Source: ABdhPJwpPa3Tnjfr7PH9HrVwL8HXIOO/5T5vKRALoN+LCGhxb/BPekgB2t7Xf+yg/QByhOlA7d/3pA== X-Received: by 2002:a63:e709:: with SMTP id b9mr11398198pgi.153.1622246033625; Fri, 28 May 2021 16:53:53 -0700 (PDT) Received: from localhost ([2402:3a80:11db:3aa9:ad24:a4a2:844f:6a0a]) by smtp.gmail.com with ESMTPSA id f9sm4890398pfc.42.2021.05.28.16.53.52 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 28 May 2021 16:53:53 -0700 (PDT) From: Kumar Kartikeya Dwivedi To: bpf@vger.kernel.org Cc: Kumar Kartikeya Dwivedi , Alexei Starovoitov , Daniel Borkmann , Andrii Nakryiko , Martin KaFai Lau , Song Liu , Yonghong Song , John Fastabend , KP Singh , "David S. Miller" , Jakub Kicinski , Jesper Dangaard Brouer , =?utf-8?q?Toke_H=C3=B8iland-J=C3=B8rgensen?= , netdev@vger.kernel.org Subject: [PATCH RFC bpf-next 05/15] samples: bpf: convert xdp_redirect_map to use xdp_samples Date: Sat, 29 May 2021 05:22:40 +0530 Message-Id: <20210528235250.2635167-6-memxor@gmail.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20210528235250.2635167-1-memxor@gmail.com> References: <20210528235250.2635167-1-memxor@gmail.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org This uses the xdp_sample_* reorg we did in the past commits to report more statistics than just the per second packet count. Signed-off-by: Kumar Kartikeya Dwivedi --- samples/bpf/Makefile | 2 +- samples/bpf/xdp_redirect_map_kern.c | 23 +++---- samples/bpf/xdp_redirect_map_user.c | 96 +++++++++++------------------ 3 files changed, 44 insertions(+), 77 deletions(-) diff --git a/samples/bpf/Makefile b/samples/bpf/Makefile index c0c02e12e28b..ea7100c8b760 100644 --- a/samples/bpf/Makefile +++ b/samples/bpf/Makefile @@ -99,8 +99,8 @@ xdp_tx_iptunnel-objs := xdp_tx_iptunnel_user.o test_map_in_map-objs := test_map_in_map_user.o per_socket_stats_example-objs := cookie_uid_helper_example.o xdp_redirect-objs := xdp_redirect_user.o -xdp_redirect_map-objs := xdp_redirect_map_user.o xdp_redirect_map_multi-objs := xdp_redirect_map_multi_user.o +xdp_redirect_map-objs := xdp_redirect_map_user.o xdp_sample_user.o xdp_redirect_cpu-objs := xdp_redirect_cpu_user.o xdp_sample_user.o xdp_monitor-objs := xdp_monitor_user.o xdp_rxq_info-objs := xdp_rxq_info_user.o diff --git a/samples/bpf/xdp_redirect_map_kern.c b/samples/bpf/xdp_redirect_map_kern.c index a92b8e567bdd..cf8b8f6d15da 100644 --- a/samples/bpf/xdp_redirect_map_kern.c +++ b/samples/bpf/xdp_redirect_map_kern.c @@ -19,6 +19,8 @@ #include #include +#include "xdp_sample_kern.h" + /* The 2nd xdp prog on egress does not support skb mode, so we define two * maps, tx_port_general and tx_port_native. */ @@ -36,16 +38,6 @@ struct { __uint(max_entries, 100); } tx_port_native SEC(".maps"); -/* Count RX packets, as XDP bpf_prog doesn't get direct TX-success - * feedback. Redirect TX errors can be caught via a tracepoint. - */ -struct { - __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); - __type(key, u32); - __type(value, long); - __uint(max_entries, 1); -} rxcnt SEC(".maps"); - /* map to store egress interface mac address */ struct { __uint(type, BPF_MAP_TYPE_ARRAY); @@ -75,7 +67,7 @@ static __always_inline int xdp_redirect_map(struct xdp_md *ctx, void *redirect_m void *data_end = (void *)(long)ctx->data_end; void *data = (void *)(long)ctx->data; struct ethhdr *eth = data; - int rc = XDP_DROP; + struct datarec *rec; long *value; u32 key = 0; u64 nh_off; @@ -83,15 +75,16 @@ static __always_inline int xdp_redirect_map(struct xdp_md *ctx, void *redirect_m nh_off = sizeof(*eth); if (data + nh_off > data_end) - return rc; + return XDP_DROP; /* constant virtual port */ vport = 0; /* count packet in global counter */ - value = bpf_map_lookup_elem(&rxcnt, &key); - if (value) - *value += 1; + rec = bpf_map_lookup_elem(&rx_cnt, &key); + if (!rec) + return XDP_ABORTED; + rec->processed++; swap_src_dst_mac(data); diff --git a/samples/bpf/xdp_redirect_map_user.c b/samples/bpf/xdp_redirect_map_user.c index ad3cdc4c07d3..42893385ba96 100644 --- a/samples/bpf/xdp_redirect_map_user.c +++ b/samples/bpf/xdp_redirect_map_user.c @@ -13,15 +13,11 @@ #include #include #include -#include -#include -#include -#include -#include #include "bpf_util.h" #include #include +#include "xdp_sample_user.h" static int ifindex_in; static int ifindex_out; @@ -31,7 +27,6 @@ static __u32 prog_id; static __u32 dummy_prog_id; static __u32 xdp_flags = XDP_FLAGS_UPDATE_IF_NOEXIST; -static int rxcnt_map_fd; static void int_exit(int sig) { @@ -62,56 +57,8 @@ static void int_exit(int sig) else printf("program on iface OUT changed, not removing\n"); } - exit(0); -} -static void poll_stats(int interval, int ifindex) -{ - unsigned int nr_cpus = bpf_num_possible_cpus(); - __u64 values[nr_cpus], prev[nr_cpus]; - - memset(prev, 0, sizeof(prev)); - - while (1) { - __u64 sum = 0; - __u32 key = 0; - int i; - - sleep(interval); - assert(bpf_map_lookup_elem(rxcnt_map_fd, &key, values) == 0); - for (i = 0; i < nr_cpus; i++) - sum += (values[i] - prev[i]); - if (sum) - printf("ifindex %i: %10llu pkt/s\n", - ifindex, sum / interval); - memcpy(prev, values, sizeof(values)); - } -} - -static int get_mac_addr(unsigned int ifindex_out, void *mac_addr) -{ - char ifname[IF_NAMESIZE]; - struct ifreq ifr; - int fd, ret = -1; - - fd = socket(AF_INET, SOCK_DGRAM, 0); - if (fd < 0) - return ret; - - if (!if_indextoname(ifindex_out, ifname)) - goto err_out; - - strcpy(ifr.ifr_name, ifname); - - if (ioctl(fd, SIOCGIFHWADDR, &ifr) != 0) - goto err_out; - - memcpy(mac_addr, ifr.ifr_hwaddr.sa_data, 6 * sizeof(char)); - ret = 0; - -err_out: - close(fd); - return ret; + sample_exit(EXIT_OK); } static void usage(const char *prog) @@ -128,6 +75,8 @@ static void usage(const char *prog) int main(int argc, char **argv) { + int mask = SAMPLE_RX_CNT | SAMPLE_REDIRECT_ERR_CNT | + SAMPLE_EXCEPTION_CNT; struct bpf_prog_load_attr prog_load_attr = { .prog_type = BPF_PROG_TYPE_UNSPEC, }; @@ -136,8 +85,11 @@ int main(int argc, char **argv) int tx_port_map_fd, tx_mac_map_fd; struct bpf_devmap_val devmap_val; struct bpf_prog_info info = {}; + char str[2 * IF_NAMESIZE + 1]; __u32 info_len = sizeof(info); + char ifname_out[IF_NAMESIZE]; const char *optstr = "FSNX"; + char ifname_in[IF_NAMESIZE]; struct bpf_object *obj; int ret, opt, key = 0; char filename[256]; @@ -182,14 +134,17 @@ int main(int argc, char **argv) if (!ifindex_out) ifindex_out = strtoul(argv[optind + 1], NULL, 0); - printf("input: %d output: %d\n", ifindex_in, ifindex_out); - snprintf(filename, sizeof(filename), "%s_kern.o", argv[0]); prog_load_attr.file = filename; if (bpf_prog_load_xattr(&prog_load_attr, &obj, &prog_fd)) return 1; + if (sample_init(obj) < 0) { + fprintf(stderr, "Failed to initialize sample\n"); + return 1; + } + if (xdp_flags & XDP_FLAGS_SKB_MODE) { prog = bpf_object__find_program_by_name(obj, "xdp_redirect_map_general"); tx_port_map_fd = bpf_object__find_map_fd_by_name(obj, "tx_port_general"); @@ -210,8 +165,7 @@ int main(int argc, char **argv) } tx_mac_map_fd = bpf_object__find_map_fd_by_name(obj, "tx_mac"); - rxcnt_map_fd = bpf_object__find_map_fd_by_name(obj, "rxcnt"); - if (tx_mac_map_fd < 0 || rxcnt_map_fd < 0) { + if (tx_mac_map_fd < 0) { printf("bpf_object__find_map_fd_by_name failed\n"); return 1; } @@ -281,8 +235,28 @@ int main(int argc, char **argv) goto out; } - poll_stats(2, ifindex_out); + if (!if_indextoname(ifindex_in, ifname_in)) { + perror("if_nametoindex"); + goto out; + } + + if (!if_indextoname(ifindex_out, ifname_out)) { + perror("if_nametoindex"); + goto out; + } + + strncpy(str, get_driver_name(ifindex_in) ?: "(err)", sizeof(str)); + + printf("Redirecting from %s (ifindex %d; driver %s) to %s (ifindex %d; driver %s)\n", + ifname_in, ifindex_in, str, ifname_out, ifindex_out, + get_driver_name(ifindex_out) ?: "(err)"); + + snprintf(str, sizeof(str), "%s->%s", ifname_in, ifname_out); + + sample_stats_poll(1, mask, str, true); -out: return 0; + +out: + return 1; } From patchwork Fri May 28 23:52:42 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kumar Kartikeya Dwivedi X-Patchwork-Id: 449864 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-15.7 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 0010FC4708D for ; Fri, 28 May 2021 23:54:05 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id D7323608FC for ; Fri, 28 May 2021 23:54:05 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229711AbhE1Xzj (ORCPT ); Fri, 28 May 2021 19:55:39 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:45450 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229700AbhE1Xzg (ORCPT ); Fri, 28 May 2021 19:55:36 -0400 Received: from mail-pf1-x441.google.com (mail-pf1-x441.google.com [IPv6:2607:f8b0:4864:20::441]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 45F58C061574; Fri, 28 May 2021 16:54:01 -0700 (PDT) Received: by mail-pf1-x441.google.com with SMTP id y15so456234pfl.4; Fri, 28 May 2021 16:54:01 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=ffTMzd8u6S5X9o61xEi2TOtbJBb+RT7uqEVsFVrSITM=; b=EVHmeksSerOZ3RDks7djP07ktmrDnrXvXrhWdZ3vgF+XtJ1A1xG1OR1HI1KhpCam7n vXM7T7b0/RVaUnvz15V5k8GUgPsnhNk5DUxxHmLn7hDscc/ewiQ5pYjfEFuiEhFyPXNP ZY650eV525HfB38d1zQxO1Ny+vNEjuE18WhVuQsawNNxiYYc4yXEXrMotTSyw/I4WJIi f04CozEDE7M3L9P0aDBzKhnBlO42appEFmCOf8u2bg740KB2+ONRjycJCZqbLDeoy52Z RLeJUaecckcy9WwAjuYsE27BrdLoKDz4vyS/Bw3BREcvyw7JH+KupU287pDIjIISS3nI CV/A== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=ffTMzd8u6S5X9o61xEi2TOtbJBb+RT7uqEVsFVrSITM=; b=kPu4wlFNFXfF8HpG5hZa4l1qqSLcTBWokeqwxRefnvElXRa3Liqeoy8jTd3N6gVccA CeIhR1Nw6yNFKYZ9EVbNhnny99dQWzUevNGOY6EcS8DbRF66ZUQiQuENzaJ4SY6Jy8uM XPdz6CHsg8ela34EQXiovIavT6Rn1kzE+onb7VR+vpDtOhP1xejm2NJUYJdgwkSmz/pS 1wHP8OFqwFtkFCkUQZP3xz3NJL5YaWuEdcD7SM9ozMRkMKL3RbaFkEiHk1Ec4oyomIOU fKPN2EL4mo47Gh814iYuynbu6NVv9de6+LRhMOmEy00hrgu8OaBXjPwKVZehUf4wBsWN 9biA== X-Gm-Message-State: AOAM533lX9pbSRiOk80uY8nJ22q22heLkXpVhDQTsFYeM/NG5y0mAcw4 /PPcPa99wYFHAN0Q73tuxm1yQap3BnU= X-Google-Smtp-Source: ABdhPJyC40qqjmaMQPPBdA8WE1U87cC79s2+H5K+ZSG1FlNxZrepSPfM0754nqHWRCIhR244If3f+g== X-Received: by 2002:a63:561d:: with SMTP id k29mr11402563pgb.335.1622246040605; Fri, 28 May 2021 16:54:00 -0700 (PDT) Received: from localhost ([2402:3a80:11db:3aa9:ad24:a4a2:844f:6a0a]) by smtp.gmail.com with ESMTPSA id o134sm5261417pfd.58.2021.05.28.16.53.59 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 28 May 2021 16:54:00 -0700 (PDT) From: Kumar Kartikeya Dwivedi To: bpf@vger.kernel.org Cc: Kumar Kartikeya Dwivedi , Alexei Starovoitov , Daniel Borkmann , Andrii Nakryiko , Martin KaFai Lau , Song Liu , Yonghong Song , John Fastabend , KP Singh , "David S. Miller" , Jakub Kicinski , Jesper Dangaard Brouer , =?utf-8?q?Toke_H=C3=B8iland-J=C3=B8rgensen?= , netdev@vger.kernel.org Subject: [PATCH RFC bpf-next 07/15] samples: bpf: add extended reporting for xdp redirect error Date: Sat, 29 May 2021 05:22:42 +0530 Message-Id: <20210528235250.2635167-8-memxor@gmail.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20210528235250.2635167-1-memxor@gmail.com> References: <20210528235250.2635167-1-memxor@gmail.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org This again is needed for xdp_monitor support. We also record the most common errnos, but don't report for now. A future commit that modifies output format will arrange for printing it properly. Signed-off-by: Kumar Kartikeya Dwivedi --- samples/bpf/xdp_sample_kern.h | 53 +++++++++++++++++++++++++++--- samples/bpf/xdp_sample_user.c | 62 +++++++++++++++++++++++++++-------- samples/bpf/xdp_sample_user.h | 13 +++++++- 3 files changed, 108 insertions(+), 20 deletions(-) diff --git a/samples/bpf/xdp_sample_kern.h b/samples/bpf/xdp_sample_kern.h index 3b85d71434d3..4131b9cb1ec4 100644 --- a/samples/bpf/xdp_sample_kern.h +++ b/samples/bpf/xdp_sample_kern.h @@ -7,6 +7,11 @@ #define MAX_CPUS 64 +#define EINVAL 22 +#define ENETDOWN 100 +#define EMSGSIZE 90 +#define EOPNOTSUPP 95 + /* Common stats data record to keep userspace more simple */ struct datarec { __u64 processed; @@ -35,8 +40,11 @@ struct { __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); __type(key, u32); __type(value, struct datarec); - __uint(max_entries, 2); - /* TODO: have entries for all possible errno's */ + __uint(max_entries, 2 + + 1 /* EINVAL */ + + 1 /* ENETDOWN */ + + 1 /* EMSGSIZE */ + + 1 /* EOPNOTSUPP */); } redirect_err_cnt SEC(".maps"); /* Used by trace point */ @@ -91,6 +99,25 @@ enum { XDP_REDIRECT_ERROR = 1 }; +static __always_inline +__u32 xdp_get_err_key(int err) +{ + switch (err) { + case 0: + return 0; + case -EINVAL: + return 2; + case -ENETDOWN: + return 3; + case -EMSGSIZE: + return 4; + case -EOPNOTSUPP: + return 5; + default: + return 1; + } +} + static __always_inline int xdp_redirect_collect_stat(struct xdp_redirect_ctx *ctx) { @@ -98,13 +125,15 @@ int xdp_redirect_collect_stat(struct xdp_redirect_ctx *ctx) struct datarec *rec; int err = ctx->err; - if (!err) - key = XDP_REDIRECT_SUCCESS; + key = xdp_get_err_key(err); rec = bpf_map_lookup_elem(&redirect_err_cnt, &key); if (!rec) return 0; - rec->dropped += 1; + if (key) + rec->dropped++; + else + rec->processed++; return 0; /* Indicate event was filtered (no further processing)*/ /* @@ -127,6 +156,20 @@ int trace_xdp_redirect_map_err(struct xdp_redirect_ctx *ctx) return xdp_redirect_collect_stat(ctx); } +/* Likely unloaded when prog starts */ +SEC("tracepoint/xdp/xdp_redirect") +int trace_xdp_redirect(struct xdp_redirect_ctx *ctx) +{ + return xdp_redirect_collect_stat(ctx); +} + +/* Likely unloaded when prog starts */ +SEC("tracepoint/xdp/xdp_redirect_map") +int trace_xdp_redirect_map(struct xdp_redirect_ctx *ctx) +{ + return xdp_redirect_collect_stat(ctx); +} + /* Tracepoint format: /sys/kernel/debug/tracing/events/xdp/xdp_exception/format * Code in: kernel/include/trace/events/xdp.h */ diff --git a/samples/bpf/xdp_sample_user.c b/samples/bpf/xdp_sample_user.c index 56cd79ba303a..29410d551574 100644 --- a/samples/bpf/xdp_sample_user.c +++ b/samples/bpf/xdp_sample_user.c @@ -121,7 +121,8 @@ struct stats_record *alloc_stats_record(void) } memset(rec, 0, size); rec->rx_cnt.cpu = alloc_record_per_cpu(); - rec->redir_err.cpu = alloc_record_per_cpu(); + rec->redir_err[0].cpu = alloc_record_per_cpu(); + rec->redir_err[1].cpu = alloc_record_per_cpu(); rec->kthread.cpu = alloc_record_per_cpu(); rec->exception.cpu = alloc_record_per_cpu(); rec->devmap_xmit.cpu = alloc_record_per_cpu(); @@ -140,7 +141,8 @@ void free_stats_record(struct stats_record *r) free(r->devmap_xmit.cpu); free(r->exception.cpu); free(r->kthread.cpu); - free(r->redir_err.cpu); + free(r->redir_err[1].cpu); + free(r->redir_err[0].cpu); free(r->rx_cnt.cpu); free(r); } @@ -332,31 +334,54 @@ static void stats_print_cpumap_kthread(struct stats_record *stats_rec, printf(fm2_k, "cpumap_kthread", "total", pps, drop, err, e_str); } +static void stats_print_redirect_cnt(struct stats_record *stats_rec, + struct stats_record *stats_prev, + unsigned int nr_cpus) +{ + char *fmt1 = "%-15s %-7d %'-14.0f %'-11.0f %s\n"; + char *fmt2 = "%-15s %-7s %'-14.0f %'-11.0f %s\n"; + struct record *rec, *prev; + double t, pps; + int i; + + rec = &stats_rec->redir_err[0]; + prev = &stats_prev->redir_err[0]; + t = calc_period(rec, prev); + for (i = 0; i < nr_cpus; i++) { + struct datarec *r = &rec->cpu[i]; + struct datarec *p = &prev->cpu[i]; + + pps = calc_pps(r, p, t); + if (pps > 0) + printf(fmt1, "redirect", i, pps, 0.0, "Success"); + } + pps = calc_pps(&rec->total, &prev->total, t); + printf(fmt2, "redirect", "total", pps, 0.0, "Success"); +} + static void stats_print_redirect_err_cnt(struct stats_record *stats_rec, struct stats_record *stats_prev, unsigned int nr_cpus) { - char *fmt_err = "%-15s %-7d %'-14.0f %'-11.0f\n"; - char *fm2_err = "%-15s %-7s %'-14.0f %'-11.0f\n"; + char *fmt1 = "%-15s %-7d %'-14.0f %'-11.0f %s\n"; + char *fmt2 = "%-15s %-7s %'-14.0f %'-11.0f %s\n"; struct record *rec, *prev; - double t, pps, drop; + double t, drop; int i; - rec = &stats_rec->redir_err; - prev = &stats_prev->redir_err; + rec = &stats_rec->redir_err[1]; + prev = &stats_prev->redir_err[1]; t = calc_period(rec, prev); for (i = 0; i < nr_cpus; i++) { struct datarec *r = &rec->cpu[i]; struct datarec *p = &prev->cpu[i]; - pps = calc_pps(r, p, t); drop = calc_drop_pps(r, p, t); - if (pps > 0) - printf(fmt_err, "redirect_err", i, pps, drop); + if (drop > 0) + printf(fmt1, "redirect", i, 0.0, drop, "Error"); } - pps = calc_pps(&rec->total, &prev->total, t); drop = calc_drop_pps(&rec->total, &prev->total, t); - printf(fm2_err, "redirect_err", "total", pps, drop); + printf(fmt2, "redirect", "total", 0.0, drop, "Error"); } static void stats_print_exception_cnt(struct stats_record *stats_rec, @@ -522,8 +547,14 @@ void sample_stats_collect(int mask, struct stats_record *rec) if (mask & SAMPLE_RX_CNT) map_collect_percpu(map_fds[RX_CNT], 0, &rec->rx_cnt); - if (mask & SAMPLE_REDIRECT_ERR_CNT) - map_collect_percpu(map_fds[REDIRECT_ERR_CNT], 1, &rec->redir_err); + /* Success case */ + if (mask & SAMPLE_REDIRECT_CNT) + map_collect_percpu(map_fds[REDIRECT_ERR_CNT], 0, &rec->redir_err[0]); + + if (mask & SAMPLE_REDIRECT_ERR_CNT) { + for (i = 1; i < XDP_REDIRECT_ERR_MAX; i++) + map_collect_percpu(map_fds[REDIRECT_ERR_CNT], i, &rec->redir_err[i]); + } if (mask & SAMPLE_CPUMAP_ENQUEUE_CNT) for (i = 0; i < n_cpus; i++) @@ -551,6 +582,9 @@ void sample_stats_print(int mask, struct stats_record *cur, if (mask & SAMPLE_RX_CNT) stats_print_rx_cnt(cur, prev, nr_cpus); + if (mask & SAMPLE_REDIRECT_CNT) + stats_print_redirect_cnt(cur, prev, nr_cpus); + if (mask & SAMPLE_REDIRECT_ERR_CNT) stats_print_redirect_err_cnt(cur, prev, nr_cpus); diff --git a/samples/bpf/xdp_sample_user.h b/samples/bpf/xdp_sample_user.h index 75a4ea4b55ad..a3a3c746e73e 100644 --- a/samples/bpf/xdp_sample_user.h +++ b/samples/bpf/xdp_sample_user.h @@ -14,6 +14,8 @@ enum map_type { }; enum tp_type { + TP_REDIRECT_CNT, + TP_REDIRECT_MAP_CNT, TP_REDIRECT_ERR_CNT, TP_REDIRECT_MAP_ERR_CNT, TP_CPUMAP_ENQUEUE_CNT, @@ -30,6 +32,7 @@ enum stats_mask { SAMPLE_CPUMAP_KTHREAD_CNT = 1U << 4, SAMPLE_EXCEPTION_CNT = 1U << 5, SAMPLE_DEVMAP_XMIT_CNT = 1U << 6, + SAMPLE_REDIRECT_CNT = 1U << 7, }; static const char *const map_type_strings[] = { @@ -54,6 +57,14 @@ extern int tp_cnt; #define EXIT_FAIL_BPF 4 #define EXIT_FAIL_MEM 5 +#define XDP_REDIRECT_ERR_MAX 6 + +static const char *xdp_redirect_err_names[XDP_REDIRECT_ERR_MAX] = { + /* Key=1 keeps unknown errors */ + "Success", "Unknown", "EINVAL", "ENETDOWN", "EMSGSIZE", + "EOPNOTSUPP", +}; + /* Common stats data record shared with _kern.c */ struct datarec { __u64 processed; @@ -75,7 +86,7 @@ struct record { struct stats_record { struct record rx_cnt; - struct record redir_err; + struct record redir_err[XDP_REDIRECT_ERR_MAX]; struct record kthread; struct record exception; struct record devmap_xmit; From patchwork Fri May 28 23:52:44 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kumar Kartikeya Dwivedi X-Patchwork-Id: 449863 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-15.7 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 61F06C4708D for ; Fri, 28 May 2021 23:54:15 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 454876135F for ; Fri, 28 May 2021 23:54:15 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229755AbhE1Xzs (ORCPT ); Fri, 28 May 2021 19:55:48 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:45476 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229724AbhE1Xzp (ORCPT ); Fri, 28 May 2021 19:55:45 -0400 Received: from mail-pl1-x644.google.com (mail-pl1-x644.google.com [IPv6:2607:f8b0:4864:20::644]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id D2708C061574; Fri, 28 May 2021 16:54:08 -0700 (PDT) Received: by mail-pl1-x644.google.com with SMTP id v13so2338625ple.9; Fri, 28 May 2021 16:54:08 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=iRj+jj4JHScG7zHlnmdQCZKLe5g9HZ0AbhyTur65Bto=; b=UievWkFLn4zDg6FyifgEzywdbvF2y0ls4pbeATErK5cVWZ8yISu5OBKrz76R5wWHyq odFMfRy82naslinfeMcVVAaxjyUyFCuQS+/qZuIX2gPMnbAsY1LIuUSACnAAWl6/pH4K HMg66aqFtOzvZI4nN8KVfpvJbV+17+UoM6l+BhWj/ECyeGiwuLo96H0ya+VRYWPuvyH5 AuqRw/fXpVALqp7vOm9P7L0XZizzxLl2iOu490fE7PlS6CcXMc9PdMC/l/PK1WREPA5T JpK1Lnz3I2/MGuCy4qJKUpwJ3Vr8YSmOZgx3duKR5jUCNxKfmBEPmPN+jnKtXjxBVgCc MJZA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=iRj+jj4JHScG7zHlnmdQCZKLe5g9HZ0AbhyTur65Bto=; b=Z+8k+3/V/PaNa8nsGTP1FOUnJS2M6e8NWqRW1SiP5S6jz5V1ZLKeXbmnwt+DGBbAUe 7v4BQ+Bj+a4nHzMqWkLXvqBgX/SFRL6zbu35j/P3joQk1jSDrrotU8Sv1A+e7NXnST4e MqxbqsopLAMFf63QMNXQt5fOaG5A9qCVxJGMmuxvE1yqricg+7Ov1mWl5KIkU99cGL/1 LBzhfOBz14G07Hj+blBMZ3Dmd9Q8Ohc8+kIxF4QQkTp8DQztaxigrZNKpPGaWdLf4NTb hNSDVZasRK1bam9dYwLZ41ySnGkwzTXYq4yywJRdFFa5aiwxYzG83dhwauQ6CBjeWPWA HESQ== X-Gm-Message-State: AOAM533ftrEoYGDb3rCOPCIHkwrO5OwmiHqpQlEvEwSyX42N+cZUORG2 +JDEwR4lixnb/Bgzq/tvW32k3Lfkl8k= X-Google-Smtp-Source: ABdhPJyZ1ubF5RXYhRzVpUqIw15mzUbFe4lMSuyH9zP5A1qj4s40FDAJtgLBikpYxpaFWxzmkTnGsg== X-Received: by 2002:a17:90a:288:: with SMTP id w8mr7074092pja.111.1622246047857; Fri, 28 May 2021 16:54:07 -0700 (PDT) Received: from localhost ([2402:3a80:11db:3aa9:ad24:a4a2:844f:6a0a]) by smtp.gmail.com with ESMTPSA id 6sm5321155pjm.21.2021.05.28.16.54.06 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 28 May 2021 16:54:07 -0700 (PDT) From: Kumar Kartikeya Dwivedi To: bpf@vger.kernel.org Cc: Kumar Kartikeya Dwivedi , Alexei Starovoitov , Daniel Borkmann , Andrii Nakryiko , Martin KaFai Lau , Song Liu , Yonghong Song , John Fastabend , KP Singh , "David S. Miller" , Jakub Kicinski , Jesper Dangaard Brouer , =?utf-8?q?Toke_H=C3=B8iland-J=C3=B8rgensen?= , netdev@vger.kernel.org Subject: [PATCH RFC bpf-next 09/15] samples: bpf: convert xdp_monitor to use xdp_samples Date: Sat, 29 May 2021 05:22:44 +0530 Message-Id: <20210528235250.2635167-10-memxor@gmail.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20210528235250.2635167-1-memxor@gmail.com> References: <20210528235250.2635167-1-memxor@gmail.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org This reuses the samples support added so far. Signed-off-by: Kumar Kartikeya Dwivedi --- samples/bpf/Makefile | 2 +- samples/bpf/xdp_monitor_kern.c | 253 +------------ samples/bpf/xdp_monitor_user.c | 625 +-------------------------------- samples/bpf/xdp_sample_kern.h | 6 +- 4 files changed, 23 insertions(+), 863 deletions(-) diff --git a/samples/bpf/Makefile b/samples/bpf/Makefile index ea7100c8b760..8750233dcf07 100644 --- a/samples/bpf/Makefile +++ b/samples/bpf/Makefile @@ -102,7 +102,7 @@ xdp_redirect-objs := xdp_redirect_user.o xdp_redirect_map_multi-objs := xdp_redirect_map_multi_user.o xdp_redirect_map-objs := xdp_redirect_map_user.o xdp_sample_user.o xdp_redirect_cpu-objs := xdp_redirect_cpu_user.o xdp_sample_user.o -xdp_monitor-objs := xdp_monitor_user.o +xdp_monitor-objs := xdp_monitor_user.o xdp_sample_user.o xdp_rxq_info-objs := xdp_rxq_info_user.o syscall_tp-objs := syscall_tp_user.o cpustat-objs := cpustat_user.o diff --git a/samples/bpf/xdp_monitor_kern.c b/samples/bpf/xdp_monitor_kern.c index 5c955b812c47..46c4fe4d7878 100644 --- a/samples/bpf/xdp_monitor_kern.c +++ b/samples/bpf/xdp_monitor_kern.c @@ -3,255 +3,6 @@ * * XDP monitor tool, based on tracepoints */ -#include -#include +#include "xdp_sample_kern.h" -struct { - __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); - __type(key, u32); - __type(value, u64); - __uint(max_entries, 2); - /* TODO: have entries for all possible errno's */ -} redirect_err_cnt SEC(".maps"); - -#define XDP_UNKNOWN XDP_REDIRECT + 1 -struct { - __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); - __type(key, u32); - __type(value, u64); - __uint(max_entries, XDP_UNKNOWN + 1); -} exception_cnt SEC(".maps"); - -/* Tracepoint format: /sys/kernel/debug/tracing/events/xdp/xdp_redirect/format - * Code in: kernel/include/trace/events/xdp.h - */ -struct xdp_redirect_ctx { - u64 __pad; // First 8 bytes are not accessible by bpf code - int prog_id; // offset:8; size:4; signed:1; - u32 act; // offset:12 size:4; signed:0; - int ifindex; // offset:16 size:4; signed:1; - int err; // offset:20 size:4; signed:1; - int to_ifindex; // offset:24 size:4; signed:1; - u32 map_id; // offset:28 size:4; signed:0; - int map_index; // offset:32 size:4; signed:1; -}; // offset:36 - -enum { - XDP_REDIRECT_SUCCESS = 0, - XDP_REDIRECT_ERROR = 1 -}; - -static __always_inline -int xdp_redirect_collect_stat(struct xdp_redirect_ctx *ctx) -{ - u32 key = XDP_REDIRECT_ERROR; - int err = ctx->err; - u64 *cnt; - - if (!err) - key = XDP_REDIRECT_SUCCESS; - - cnt = bpf_map_lookup_elem(&redirect_err_cnt, &key); - if (!cnt) - return 1; - *cnt += 1; - - return 0; /* Indicate event was filtered (no further processing)*/ - /* - * Returning 1 here would allow e.g. a perf-record tracepoint - * to see and record these events, but it doesn't work well - * in-practice as stopping perf-record also unload this - * bpf_prog. Plus, there is additional overhead of doing so. - */ -} - -SEC("tracepoint/xdp/xdp_redirect_err") -int trace_xdp_redirect_err(struct xdp_redirect_ctx *ctx) -{ - return xdp_redirect_collect_stat(ctx); -} - - -SEC("tracepoint/xdp/xdp_redirect_map_err") -int trace_xdp_redirect_map_err(struct xdp_redirect_ctx *ctx) -{ - return xdp_redirect_collect_stat(ctx); -} - -/* Likely unloaded when prog starts */ -SEC("tracepoint/xdp/xdp_redirect") -int trace_xdp_redirect(struct xdp_redirect_ctx *ctx) -{ - return xdp_redirect_collect_stat(ctx); -} - -/* Likely unloaded when prog starts */ -SEC("tracepoint/xdp/xdp_redirect_map") -int trace_xdp_redirect_map(struct xdp_redirect_ctx *ctx) -{ - return xdp_redirect_collect_stat(ctx); -} - -/* Tracepoint format: /sys/kernel/debug/tracing/events/xdp/xdp_exception/format - * Code in: kernel/include/trace/events/xdp.h - */ -struct xdp_exception_ctx { - u64 __pad; // First 8 bytes are not accessible by bpf code - int prog_id; // offset:8; size:4; signed:1; - u32 act; // offset:12; size:4; signed:0; - int ifindex; // offset:16; size:4; signed:1; -}; - -SEC("tracepoint/xdp/xdp_exception") -int trace_xdp_exception(struct xdp_exception_ctx *ctx) -{ - u64 *cnt; - u32 key; - - key = ctx->act; - if (key > XDP_REDIRECT) - key = XDP_UNKNOWN; - - cnt = bpf_map_lookup_elem(&exception_cnt, &key); - if (!cnt) - return 1; - *cnt += 1; - - return 0; -} - -/* Common stats data record shared with _user.c */ -struct datarec { - u64 processed; - u64 dropped; - u64 info; - u64 err; -}; -#define MAX_CPUS 64 - -struct { - __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); - __type(key, u32); - __type(value, struct datarec); - __uint(max_entries, MAX_CPUS); -} cpumap_enqueue_cnt SEC(".maps"); - -struct { - __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); - __type(key, u32); - __type(value, struct datarec); - __uint(max_entries, 1); -} cpumap_kthread_cnt SEC(".maps"); - -/* Tracepoint: /sys/kernel/debug/tracing/events/xdp/xdp_cpumap_enqueue/format - * Code in: kernel/include/trace/events/xdp.h - */ -struct cpumap_enqueue_ctx { - u64 __pad; // First 8 bytes are not accessible by bpf code - int map_id; // offset:8; size:4; signed:1; - u32 act; // offset:12; size:4; signed:0; - int cpu; // offset:16; size:4; signed:1; - unsigned int drops; // offset:20; size:4; signed:0; - unsigned int processed; // offset:24; size:4; signed:0; - int to_cpu; // offset:28; size:4; signed:1; -}; - -SEC("tracepoint/xdp/xdp_cpumap_enqueue") -int trace_xdp_cpumap_enqueue(struct cpumap_enqueue_ctx *ctx) -{ - u32 to_cpu = ctx->to_cpu; - struct datarec *rec; - - if (to_cpu >= MAX_CPUS) - return 1; - - rec = bpf_map_lookup_elem(&cpumap_enqueue_cnt, &to_cpu); - if (!rec) - return 0; - rec->processed += ctx->processed; - rec->dropped += ctx->drops; - - /* Record bulk events, then userspace can calc average bulk size */ - if (ctx->processed > 0) - rec->info += 1; - - return 0; -} - -/* Tracepoint: /sys/kernel/debug/tracing/events/xdp/xdp_cpumap_kthread/format - * Code in: kernel/include/trace/events/xdp.h - */ -struct cpumap_kthread_ctx { - u64 __pad; // First 8 bytes are not accessible by bpf code - int map_id; // offset:8; size:4; signed:1; - u32 act; // offset:12; size:4; signed:0; - int cpu; // offset:16; size:4; signed:1; - unsigned int drops; // offset:20; size:4; signed:0; - unsigned int processed; // offset:24; size:4; signed:0; - int sched; // offset:28; size:4; signed:1; -}; - -SEC("tracepoint/xdp/xdp_cpumap_kthread") -int trace_xdp_cpumap_kthread(struct cpumap_kthread_ctx *ctx) -{ - struct datarec *rec; - u32 key = 0; - - rec = bpf_map_lookup_elem(&cpumap_kthread_cnt, &key); - if (!rec) - return 0; - rec->processed += ctx->processed; - rec->dropped += ctx->drops; - - /* Count times kthread yielded CPU via schedule call */ - if (ctx->sched) - rec->info++; - - return 0; -} - -struct { - __uint(type, BPF_MAP_TYPE_PERCPU_ARRAY); - __type(key, u32); - __type(value, struct datarec); - __uint(max_entries, 1); -} devmap_xmit_cnt SEC(".maps"); - -/* Tracepoint: /sys/kernel/debug/tracing/events/xdp/xdp_devmap_xmit/format - * Code in: kernel/include/trace/events/xdp.h - */ -struct devmap_xmit_ctx { - u64 __pad; // First 8 bytes are not accessible by bpf code - int from_ifindex; // offset:8; size:4; signed:1; - u32 act; // offset:12; size:4; signed:0; - int to_ifindex; // offset:16; size:4; signed:1; - int drops; // offset:20; size:4; signed:1; - int sent; // offset:24; size:4; signed:1; - int err; // offset:28; size:4; signed:1; -}; - -SEC("tracepoint/xdp/xdp_devmap_xmit") -int trace_xdp_devmap_xmit(struct devmap_xmit_ctx *ctx) -{ - struct datarec *rec; - u32 key = 0; - - rec = bpf_map_lookup_elem(&devmap_xmit_cnt, &key); - if (!rec) - return 0; - rec->processed += ctx->sent; - rec->dropped += ctx->drops; - - /* Record bulk events, then userspace can calc average bulk size */ - rec->info += 1; - - /* Record error cases, where no frame were sent */ - if (ctx->err) - rec->err++; - - /* Catch API error of drv ndo_xdp_xmit sent more than count */ - if (ctx->drops < 0) - rec->err++; - - return 1; -} +char _license[] SEC("license") = "GPL"; diff --git a/samples/bpf/xdp_monitor_user.c b/samples/bpf/xdp_monitor_user.c index 49ebc49aefc3..babb9fcc1a17 100644 --- a/samples/bpf/xdp_monitor_user.c +++ b/samples/bpf/xdp_monitor_user.c @@ -30,32 +30,9 @@ static const char *__doc_err_only__= #include #include #include "bpf_util.h" +#include "xdp_sample_user.h" -enum map_type { - REDIRECT_ERR_CNT, - EXCEPTION_CNT, - CPUMAP_ENQUEUE_CNT, - CPUMAP_KTHREAD_CNT, - DEVMAP_XMIT_CNT, -}; - -static const char *const map_type_strings[] = { - [REDIRECT_ERR_CNT] = "redirect_err_cnt", - [EXCEPTION_CNT] = "exception_cnt", - [CPUMAP_ENQUEUE_CNT] = "cpumap_enqueue_cnt", - [CPUMAP_KTHREAD_CNT] = "cpumap_kthread_cnt", - [DEVMAP_XMIT_CNT] = "devmap_xmit_cnt", -}; - -#define NUM_MAP 5 -#define NUM_TP 8 - -static int tp_cnt; -static int map_cnt; -static int verbose = 1; static bool debug = false; -struct bpf_map *map_data[NUM_MAP] = {}; -struct bpf_link *tp_links[NUM_TP] = {}; struct bpf_object *obj; static const struct option long_options[] = { @@ -68,12 +45,8 @@ static const struct option long_options[] = { static void int_exit(int sig) { - /* Detach tracepoints */ - while (tp_cnt) - bpf_link__destroy(tp_links[--tp_cnt]); - bpf_object__close(obj); - exit(0); + sample_exit(EXIT_OK); } /* C standard specifies two constants, EXIT_SUCCESS(0) and EXIT_FAILURE(1) */ @@ -100,557 +73,6 @@ static void usage(char *argv[]) printf("\n"); } -#define NANOSEC_PER_SEC 1000000000 /* 10^9 */ -static __u64 gettime(void) -{ - struct timespec t; - int res; - - res = clock_gettime(CLOCK_MONOTONIC, &t); - if (res < 0) { - fprintf(stderr, "Error with gettimeofday! (%i)\n", res); - exit(EXIT_FAILURE); - } - return (__u64) t.tv_sec * NANOSEC_PER_SEC + t.tv_nsec; -} - -enum { - REDIR_SUCCESS = 0, - REDIR_ERROR = 1, -}; -#define REDIR_RES_MAX 2 -static const char *redir_names[REDIR_RES_MAX] = { - [REDIR_SUCCESS] = "Success", - [REDIR_ERROR] = "Error", -}; -static const char *err2str(int err) -{ - if (err < REDIR_RES_MAX) - return redir_names[err]; - return NULL; -} -/* enum xdp_action */ -#define XDP_UNKNOWN XDP_REDIRECT + 1 -#define XDP_ACTION_MAX (XDP_UNKNOWN + 1) -static const char *xdp_action_names[XDP_ACTION_MAX] = { - [XDP_ABORTED] = "XDP_ABORTED", - [XDP_DROP] = "XDP_DROP", - [XDP_PASS] = "XDP_PASS", - [XDP_TX] = "XDP_TX", - [XDP_REDIRECT] = "XDP_REDIRECT", - [XDP_UNKNOWN] = "XDP_UNKNOWN", -}; -static const char *action2str(int action) -{ - if (action < XDP_ACTION_MAX) - return xdp_action_names[action]; - return NULL; -} - -/* Common stats data record shared with _kern.c */ -struct datarec { - __u64 processed; - __u64 dropped; - __u64 info; - __u64 err; -}; -#define MAX_CPUS 64 - -/* Userspace structs for collection of stats from maps */ -struct record { - __u64 timestamp; - struct datarec total; - struct datarec *cpu; -}; -struct u64rec { - __u64 processed; -}; -struct record_u64 { - /* record for _kern side __u64 values */ - __u64 timestamp; - struct u64rec total; - struct u64rec *cpu; -}; - -struct stats_record { - struct record_u64 xdp_redirect[REDIR_RES_MAX]; - struct record_u64 xdp_exception[XDP_ACTION_MAX]; - struct record xdp_cpumap_kthread; - struct record xdp_cpumap_enqueue[MAX_CPUS]; - struct record xdp_devmap_xmit; -}; - -static bool map_collect_record(int fd, __u32 key, struct record *rec) -{ - /* For percpu maps, userspace gets a value per possible CPU */ - unsigned int nr_cpus = bpf_num_possible_cpus(); - struct datarec values[nr_cpus]; - __u64 sum_processed = 0; - __u64 sum_dropped = 0; - __u64 sum_info = 0; - __u64 sum_err = 0; - int i; - - if ((bpf_map_lookup_elem(fd, &key, values)) != 0) { - fprintf(stderr, - "ERR: bpf_map_lookup_elem failed key:0x%X\n", key); - return false; - } - /* Get time as close as possible to reading map contents */ - rec->timestamp = gettime(); - - /* Record and sum values from each CPU */ - for (i = 0; i < nr_cpus; i++) { - rec->cpu[i].processed = values[i].processed; - sum_processed += values[i].processed; - rec->cpu[i].dropped = values[i].dropped; - sum_dropped += values[i].dropped; - rec->cpu[i].info = values[i].info; - sum_info += values[i].info; - rec->cpu[i].err = values[i].err; - sum_err += values[i].err; - } - rec->total.processed = sum_processed; - rec->total.dropped = sum_dropped; - rec->total.info = sum_info; - rec->total.err = sum_err; - return true; -} - -static bool map_collect_record_u64(int fd, __u32 key, struct record_u64 *rec) -{ - /* For percpu maps, userspace gets a value per possible CPU */ - unsigned int nr_cpus = bpf_num_possible_cpus(); - struct u64rec values[nr_cpus]; - __u64 sum_total = 0; - int i; - - if ((bpf_map_lookup_elem(fd, &key, values)) != 0) { - fprintf(stderr, - "ERR: bpf_map_lookup_elem failed key:0x%X\n", key); - return false; - } - /* Get time as close as possible to reading map contents */ - rec->timestamp = gettime(); - - /* Record and sum values from each CPU */ - for (i = 0; i < nr_cpus; i++) { - rec->cpu[i].processed = values[i].processed; - sum_total += values[i].processed; - } - rec->total.processed = sum_total; - return true; -} - -static double calc_period(struct record *r, struct record *p) -{ - double period_ = 0; - __u64 period = 0; - - period = r->timestamp - p->timestamp; - if (period > 0) - period_ = ((double) period / NANOSEC_PER_SEC); - - return period_; -} - -static double calc_period_u64(struct record_u64 *r, struct record_u64 *p) -{ - double period_ = 0; - __u64 period = 0; - - period = r->timestamp - p->timestamp; - if (period > 0) - period_ = ((double) period / NANOSEC_PER_SEC); - - return period_; -} - -static double calc_pps(struct datarec *r, struct datarec *p, double period) -{ - __u64 packets = 0; - double pps = 0; - - if (period > 0) { - packets = r->processed - p->processed; - pps = packets / period; - } - return pps; -} - -static double calc_pps_u64(struct u64rec *r, struct u64rec *p, double period) -{ - __u64 packets = 0; - double pps = 0; - - if (period > 0) { - packets = r->processed - p->processed; - pps = packets / period; - } - return pps; -} - -static double calc_drop(struct datarec *r, struct datarec *p, double period) -{ - __u64 packets = 0; - double pps = 0; - - if (period > 0) { - packets = r->dropped - p->dropped; - pps = packets / period; - } - return pps; -} - -static double calc_info(struct datarec *r, struct datarec *p, double period) -{ - __u64 packets = 0; - double pps = 0; - - if (period > 0) { - packets = r->info - p->info; - pps = packets / period; - } - return pps; -} - -static double calc_err(struct datarec *r, struct datarec *p, double period) -{ - __u64 packets = 0; - double pps = 0; - - if (period > 0) { - packets = r->err - p->err; - pps = packets / period; - } - return pps; -} - -static void stats_print(struct stats_record *stats_rec, - struct stats_record *stats_prev, - bool err_only) -{ - unsigned int nr_cpus = bpf_num_possible_cpus(); - int rec_i = 0, i, to_cpu; - double t = 0, pps = 0; - - /* Header */ - printf("%-15s %-7s %-12s %-12s %-9s\n", - "XDP-event", "CPU:to", "pps", "drop-pps", "extra-info"); - - /* tracepoint: xdp:xdp_redirect_* */ - if (err_only) - rec_i = REDIR_ERROR; - - for (; rec_i < REDIR_RES_MAX; rec_i++) { - struct record_u64 *rec, *prev; - char *fmt1 = "%-15s %-7d %'-12.0f %'-12.0f %s\n"; - char *fmt2 = "%-15s %-7s %'-12.0f %'-12.0f %s\n"; - - rec = &stats_rec->xdp_redirect[rec_i]; - prev = &stats_prev->xdp_redirect[rec_i]; - t = calc_period_u64(rec, prev); - - for (i = 0; i < nr_cpus; i++) { - struct u64rec *r = &rec->cpu[i]; - struct u64rec *p = &prev->cpu[i]; - - pps = calc_pps_u64(r, p, t); - if (pps > 0) - printf(fmt1, "XDP_REDIRECT", i, - rec_i ? 0.0: pps, rec_i ? pps : 0.0, - err2str(rec_i)); - } - pps = calc_pps_u64(&rec->total, &prev->total, t); - printf(fmt2, "XDP_REDIRECT", "total", - rec_i ? 0.0: pps, rec_i ? pps : 0.0, err2str(rec_i)); - } - - /* tracepoint: xdp:xdp_exception */ - for (rec_i = 0; rec_i < XDP_ACTION_MAX; rec_i++) { - struct record_u64 *rec, *prev; - char *fmt1 = "%-15s %-7d %'-12.0f %'-12.0f %s\n"; - char *fmt2 = "%-15s %-7s %'-12.0f %'-12.0f %s\n"; - - rec = &stats_rec->xdp_exception[rec_i]; - prev = &stats_prev->xdp_exception[rec_i]; - t = calc_period_u64(rec, prev); - - for (i = 0; i < nr_cpus; i++) { - struct u64rec *r = &rec->cpu[i]; - struct u64rec *p = &prev->cpu[i]; - - pps = calc_pps_u64(r, p, t); - if (pps > 0) - printf(fmt1, "Exception", i, - 0.0, pps, action2str(rec_i)); - } - pps = calc_pps_u64(&rec->total, &prev->total, t); - if (pps > 0) - printf(fmt2, "Exception", "total", - 0.0, pps, action2str(rec_i)); - } - - /* cpumap enqueue stats */ - for (to_cpu = 0; to_cpu < MAX_CPUS; to_cpu++) { - char *fmt1 = "%-15s %3d:%-3d %'-12.0f %'-12.0f %'-10.2f %s\n"; - char *fmt2 = "%-15s %3s:%-3d %'-12.0f %'-12.0f %'-10.2f %s\n"; - struct record *rec, *prev; - char *info_str = ""; - double drop, info; - - rec = &stats_rec->xdp_cpumap_enqueue[to_cpu]; - prev = &stats_prev->xdp_cpumap_enqueue[to_cpu]; - t = calc_period(rec, prev); - for (i = 0; i < nr_cpus; i++) { - struct datarec *r = &rec->cpu[i]; - struct datarec *p = &prev->cpu[i]; - - pps = calc_pps(r, p, t); - drop = calc_drop(r, p, t); - info = calc_info(r, p, t); - if (info > 0) { - info_str = "bulk-average"; - info = pps / info; /* calc average bulk size */ - } - if (pps > 0) - printf(fmt1, "cpumap-enqueue", - i, to_cpu, pps, drop, info, info_str); - } - pps = calc_pps(&rec->total, &prev->total, t); - if (pps > 0) { - drop = calc_drop(&rec->total, &prev->total, t); - info = calc_info(&rec->total, &prev->total, t); - if (info > 0) { - info_str = "bulk-average"; - info = pps / info; /* calc average bulk size */ - } - printf(fmt2, "cpumap-enqueue", - "sum", to_cpu, pps, drop, info, info_str); - } - } - - /* cpumap kthread stats */ - { - char *fmt1 = "%-15s %-7d %'-12.0f %'-12.0f %'-10.0f %s\n"; - char *fmt2 = "%-15s %-7s %'-12.0f %'-12.0f %'-10.0f %s\n"; - struct record *rec, *prev; - double drop, info; - char *i_str = ""; - - rec = &stats_rec->xdp_cpumap_kthread; - prev = &stats_prev->xdp_cpumap_kthread; - t = calc_period(rec, prev); - for (i = 0; i < nr_cpus; i++) { - struct datarec *r = &rec->cpu[i]; - struct datarec *p = &prev->cpu[i]; - - pps = calc_pps(r, p, t); - drop = calc_drop(r, p, t); - info = calc_info(r, p, t); - if (info > 0) - i_str = "sched"; - if (pps > 0 || drop > 0) - printf(fmt1, "cpumap-kthread", - i, pps, drop, info, i_str); - } - pps = calc_pps(&rec->total, &prev->total, t); - drop = calc_drop(&rec->total, &prev->total, t); - info = calc_info(&rec->total, &prev->total, t); - if (info > 0) - i_str = "sched-sum"; - printf(fmt2, "cpumap-kthread", "total", pps, drop, info, i_str); - } - - /* devmap ndo_xdp_xmit stats */ - { - char *fmt1 = "%-15s %-7d %'-12.0f %'-12.0f %'-10.2f %s %s\n"; - char *fmt2 = "%-15s %-7s %'-12.0f %'-12.0f %'-10.2f %s %s\n"; - struct record *rec, *prev; - double drop, info, err; - char *i_str = ""; - char *err_str = ""; - - rec = &stats_rec->xdp_devmap_xmit; - prev = &stats_prev->xdp_devmap_xmit; - t = calc_period(rec, prev); - for (i = 0; i < nr_cpus; i++) { - struct datarec *r = &rec->cpu[i]; - struct datarec *p = &prev->cpu[i]; - - pps = calc_pps(r, p, t); - drop = calc_drop(r, p, t); - info = calc_info(r, p, t); - err = calc_err(r, p, t); - if (info > 0) { - i_str = "bulk-average"; - info = (pps+drop) / info; /* calc avg bulk */ - } - if (err > 0) - err_str = "drv-err"; - if (pps > 0 || drop > 0) - printf(fmt1, "devmap-xmit", - i, pps, drop, info, i_str, err_str); - } - pps = calc_pps(&rec->total, &prev->total, t); - drop = calc_drop(&rec->total, &prev->total, t); - info = calc_info(&rec->total, &prev->total, t); - err = calc_err(&rec->total, &prev->total, t); - if (info > 0) { - i_str = "bulk-average"; - info = (pps+drop) / info; /* calc avg bulk */ - } - if (err > 0) - err_str = "drv-err"; - printf(fmt2, "devmap-xmit", "total", pps, drop, - info, i_str, err_str); - } - - printf("\n"); -} - -static bool stats_collect(struct stats_record *rec) -{ - int fd; - int i; - - /* TODO: Detect if someone unloaded the perf event_fd's, as - * this can happen by someone running perf-record -e - */ - - fd = bpf_map__fd(map_data[REDIRECT_ERR_CNT]); - for (i = 0; i < REDIR_RES_MAX; i++) - map_collect_record_u64(fd, i, &rec->xdp_redirect[i]); - - fd = bpf_map__fd(map_data[EXCEPTION_CNT]); - for (i = 0; i < XDP_ACTION_MAX; i++) { - map_collect_record_u64(fd, i, &rec->xdp_exception[i]); - } - - fd = bpf_map__fd(map_data[CPUMAP_ENQUEUE_CNT]); - for (i = 0; i < MAX_CPUS; i++) - map_collect_record(fd, i, &rec->xdp_cpumap_enqueue[i]); - - fd = bpf_map__fd(map_data[CPUMAP_KTHREAD_CNT]); - map_collect_record(fd, 0, &rec->xdp_cpumap_kthread); - - fd = bpf_map__fd(map_data[DEVMAP_XMIT_CNT]); - map_collect_record(fd, 0, &rec->xdp_devmap_xmit); - - return true; -} - -static void *alloc_rec_per_cpu(int record_size) -{ - unsigned int nr_cpus = bpf_num_possible_cpus(); - void *array; - - array = calloc(nr_cpus, record_size); - if (!array) { - fprintf(stderr, "Mem alloc error (nr_cpus:%u)\n", nr_cpus); - exit(EXIT_FAIL_MEM); - } - return array; -} - -static struct stats_record *alloc_stats_record(void) -{ - struct stats_record *rec; - int rec_sz; - int i; - - /* Alloc main stats_record structure */ - rec = calloc(1, sizeof(*rec)); - if (!rec) { - fprintf(stderr, "Mem alloc error\n"); - exit(EXIT_FAIL_MEM); - } - - /* Alloc stats stored per CPU for each record */ - rec_sz = sizeof(struct u64rec); - for (i = 0; i < REDIR_RES_MAX; i++) - rec->xdp_redirect[i].cpu = alloc_rec_per_cpu(rec_sz); - - for (i = 0; i < XDP_ACTION_MAX; i++) - rec->xdp_exception[i].cpu = alloc_rec_per_cpu(rec_sz); - - rec_sz = sizeof(struct datarec); - rec->xdp_cpumap_kthread.cpu = alloc_rec_per_cpu(rec_sz); - rec->xdp_devmap_xmit.cpu = alloc_rec_per_cpu(rec_sz); - - for (i = 0; i < MAX_CPUS; i++) - rec->xdp_cpumap_enqueue[i].cpu = alloc_rec_per_cpu(rec_sz); - - return rec; -} - -static void free_stats_record(struct stats_record *r) -{ - int i; - - for (i = 0; i < REDIR_RES_MAX; i++) - free(r->xdp_redirect[i].cpu); - - for (i = 0; i < XDP_ACTION_MAX; i++) - free(r->xdp_exception[i].cpu); - - free(r->xdp_cpumap_kthread.cpu); - free(r->xdp_devmap_xmit.cpu); - - for (i = 0; i < MAX_CPUS; i++) - free(r->xdp_cpumap_enqueue[i].cpu); - - free(r); -} - -/* Pointer swap trick */ -static inline void swap(struct stats_record **a, struct stats_record **b) -{ - struct stats_record *tmp; - - tmp = *a; - *a = *b; - *b = tmp; -} - -static void stats_poll(int interval, bool err_only) -{ - struct stats_record *rec, *prev; - - rec = alloc_stats_record(); - prev = alloc_stats_record(); - stats_collect(rec); - - if (err_only) - printf("\n%s\n", __doc_err_only__); - - /* Trick to pretty printf with thousands separators use %' */ - setlocale(LC_NUMERIC, "en_US"); - - /* Header */ - if (verbose) - printf("\n%s", __doc__); - - /* TODO Need more advanced stats on error types */ - if (verbose) { - printf(" - Stats map0: %s\n", bpf_map__name(map_data[0])); - printf(" - Stats map1: %s\n", bpf_map__name(map_data[1])); - printf("\n"); - } - fflush(stdout); - - while (1) { - swap(&prev, &rec); - stats_collect(rec); - stats_print(rec, prev, err_only); - fflush(stdout); - sleep(interval); - } - - free_stats_record(rec); - free_stats_record(prev); -} - static void print_bpf_prog_info(void) { struct bpf_program *prog; @@ -666,7 +88,7 @@ static void print_bpf_prog_info(void) i = 0; /* Maps info */ - printf("Loaded BPF prog have %d map(s)\n", map_cnt); + printf("Loaded BPF prog have %d map(s)\n", NUM_MAP); bpf_object__for_each_map(map, obj) { const char *name = bpf_map__name(map); int fd = bpf_map__fd(map); @@ -687,10 +109,11 @@ static void print_bpf_prog_info(void) int main(int argc, char **argv) { - struct bpf_program *prog; + int mask = SAMPLE_REDIRECT_ERR_CNT | SAMPLE_CPUMAP_ENQUEUE_CNT | + SAMPLE_CPUMAP_KTHREAD_CNT | SAMPLE_EXCEPTION_CNT | + SAMPLE_DEVMAP_XMIT_CNT; int longindex = 0, opt; int ret = EXIT_FAILURE; - enum map_type type; char filename[256]; /* Default settings: */ @@ -736,25 +159,9 @@ int main(int argc, char **argv) goto cleanup; } - for (type = 0; type < NUM_MAP; type++) { - map_data[type] = - bpf_object__find_map_by_name(obj, map_type_strings[type]); - - if (libbpf_get_error(map_data[type])) { - printf("ERROR: finding a map in obj file failed\n"); - goto cleanup; - } - map_cnt++; - } - - bpf_object__for_each_program(prog, obj) { - tp_links[tp_cnt] = bpf_program__attach(prog); - if (libbpf_get_error(tp_links[tp_cnt])) { - printf("ERROR: bpf_program__attach failed\n"); - tp_links[tp_cnt] = NULL; - goto cleanup; - } - tp_cnt++; + if (sample_init(obj) < 0) { + fprintf(stderr, "Failed to initialize sample\n"); + goto cleanup; } if (debug) { @@ -763,6 +170,8 @@ int main(int argc, char **argv) /* Unload/stop tracepoint event by closing bpf_link's */ if (errors_only) { + printf("%s", __doc_err_only__); + /* The bpf_link[i] depend on the order of * the functions was defined in _kern.c */ @@ -771,17 +180,13 @@ int main(int argc, char **argv) bpf_link__destroy(tp_links[3]); /* tracepoint/xdp/xdp_redirect_map */ tp_links[3] = NULL; + } else { + mask |= SAMPLE_REDIRECT_CNT; } - stats_poll(interval, errors_only); - - ret = EXIT_SUCCESS; + sample_stats_poll(interval, mask, "xdp_monitor", true); cleanup: - /* Detach tracepoints */ - while (tp_cnt) - bpf_link__destroy(tp_links[--tp_cnt]); - bpf_object__close(obj); - return ret; + sample_exit(EXIT_OK); } diff --git a/samples/bpf/xdp_sample_kern.h b/samples/bpf/xdp_sample_kern.h index ec36e7b4a3ba..dd7f7ea63166 100644 --- a/samples/bpf/xdp_sample_kern.h +++ b/samples/bpf/xdp_sample_kern.h @@ -5,7 +5,11 @@ #include #include -#define MAX_CPUS 64 +#ifndef NR_CPUS +#define NR_CPUS 64 +#endif + +#define MAX_CPUS NR_CPUS #define EINVAL 22 #define ENETDOWN 100 From patchwork Fri May 28 23:52:46 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kumar Kartikeya Dwivedi X-Patchwork-Id: 449862 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-15.7 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 73EC3C4708E for ; Fri, 28 May 2021 23:54:21 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 564E7613B4 for ; Fri, 28 May 2021 23:54:21 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229764AbhE1Xzy (ORCPT ); Fri, 28 May 2021 19:55:54 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:45530 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229744AbhE1Xzw (ORCPT ); Fri, 28 May 2021 19:55:52 -0400 Received: from mail-pg1-x541.google.com (mail-pg1-x541.google.com [IPv6:2607:f8b0:4864:20::541]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id BBD21C061574; Fri, 28 May 2021 16:54:15 -0700 (PDT) Received: by mail-pg1-x541.google.com with SMTP id j12so3699436pgh.7; Fri, 28 May 2021 16:54:15 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=HOsaKyuguNk7X64KL0+mdKcQaE9q+46io+EdBwhI/HE=; b=bPylqBLWgQa8zPT+3Zvf4SfE73L9k3zd2769uiQpzz7BIBvZr2oL6MaqXTWUhrh72S +hjIom7pR2KC0BnSo7CrGGOKKN2r0vSkSBRBFBap7jVh3e8RtGKcodmOuA8okd3dN3Uq wjG2oRVNUcTZGigpsG+DKRg7vP1ZWeIzS1H2mEqD862yHgUZgxdX5A5Ml2SeXuzm1T7W 0LxhfTWX0wMSsPvkEJx9KioJ06njDiQRRhLOAGliMDI4Ak9zx64Yp+DUAEWMDHSJShsw 0gPE2ZgnNKgSc/4AjBvcizqmfS+CQ7PlDhJmQt0kz9cSrktoGzGz/XZAfZp1BWw4LQwh Y+/w== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=HOsaKyuguNk7X64KL0+mdKcQaE9q+46io+EdBwhI/HE=; b=dZ6V3JVLc6phTk4aS3Uccec0Tg7kR8zN+uGov4TACRUrjQNeZgCe4yQnOC/fGCnaM9 HTBMSMfaAKqcU12wE09nQIK0GK/hvMkrWM0sGuMaHhEJbbRkeuZE3Li4havXd5LycnSS euN6Xdl5sBPu0WCeOWDrbPhmNnNCVGyUyE7CzdVi3r7psLmzOBkwlBOaAwdoXBVF7UlV Omqa5zNp2HR7zbl6rvqjdP6tdyeMQU6KSQsrJezn65ZaxYA2wyaH0UTD+/sFnUO3MQGW /Tz4kFEGDlZz9dmEacAVi41CskdzCnrUeXqm/sEgerVdi/tHNIvyZrwkLVeQ2KilSEDQ ffJw== X-Gm-Message-State: AOAM530nme0HixRGEvvMMDqsoUOnt2xIZ9GZw1XW/AO10UGkxNmpa/30 hS57CbHj84ms9+FpVI7xXIqf0VmVFWA= X-Google-Smtp-Source: ABdhPJwYf/eKOjmugknMYst3VHTlQU0LjqYyBRW4jUNFwsFyRrCpWn8sCuQlvtYksh2RcchgoqyV5Q== X-Received: by 2002:aa7:9a8e:0:b029:2e7:e3fd:4fa4 with SMTP id w14-20020aa79a8e0000b02902e7e3fd4fa4mr6358497pfi.63.1622246054931; Fri, 28 May 2021 16:54:14 -0700 (PDT) Received: from localhost ([2402:3a80:11db:3aa9:ad24:a4a2:844f:6a0a]) by smtp.gmail.com with ESMTPSA id y66sm4986604pgb.14.2021.05.28.16.54.14 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 28 May 2021 16:54:14 -0700 (PDT) From: Kumar Kartikeya Dwivedi To: bpf@vger.kernel.org Cc: Kumar Kartikeya Dwivedi , Alexei Starovoitov , Daniel Borkmann , Andrii Nakryiko , Martin KaFai Lau , Song Liu , Yonghong Song , John Fastabend , KP Singh , "David S. Miller" , Jakub Kicinski , Jesper Dangaard Brouer , =?utf-8?q?Toke_H=C3=B8iland-J=C3=B8rgensen?= , netdev@vger.kernel.org Subject: [PATCH RFC bpf-next 11/15] samples: bpf: print summary of session on exit Date: Sat, 29 May 2021 05:22:46 +0530 Message-Id: <20210528235250.2635167-12-memxor@gmail.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20210528235250.2635167-1-memxor@gmail.com> References: <20210528235250.2635167-1-memxor@gmail.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org This collects total statistics and prints the totals and averages for main attributes when exiting. These are collected on each polling interval. Signed-off-by: Kumar Kartikeya Dwivedi --- samples/bpf/xdp_redirect_cpu_user.c | 2 +- samples/bpf/xdp_redirect_map_user.c | 2 +- samples/bpf/xdp_sample_user.c | 141 +++++++++++++++++++++++++--- samples/bpf/xdp_sample_user.h | 22 +++-- 4 files changed, 145 insertions(+), 22 deletions(-) diff --git a/samples/bpf/xdp_redirect_cpu_user.c b/samples/bpf/xdp_redirect_cpu_user.c index 3983ed71d879..4c9f32229508 100644 --- a/samples/bpf/xdp_redirect_cpu_user.c +++ b/samples/bpf/xdp_redirect_cpu_user.c @@ -216,7 +216,7 @@ static void __stats_poll(int interval, bool use_separators, char *prog_name, for (;;) { swap(&prev, &record); sample_stats_collect(mask, record); - sample_stats_print(mask, record, prev, NULL); + sample_stats_print(mask, record, prev, NULL, interval); /* Depends on SAMPLE_CPUMAP_KTHREAD_CNT */ sample_stats_print_cpumap_remote(record, prev, bpf_num_possible_cpus(), diff --git a/samples/bpf/xdp_redirect_map_user.c b/samples/bpf/xdp_redirect_map_user.c index b2c7adad99ec..ed53dd2cd93a 100644 --- a/samples/bpf/xdp_redirect_map_user.c +++ b/samples/bpf/xdp_redirect_map_user.c @@ -75,7 +75,7 @@ static void usage(const char *prog) int main(int argc, char **argv) { - int mask = SAMPLE_RX_CNT | SAMPLE_REDIRECT_ERR_CNT | + int mask = SAMPLE_RX_CNT | SAMPLE_REDIRECT_ERR_MAP_CNT | SAMPLE_EXCEPTION_CNT | SAMPLE_DEVMAP_XMIT_CNT; struct bpf_prog_load_attr prog_load_attr = { .prog_type = BPF_PROG_TYPE_UNSPEC, diff --git a/samples/bpf/xdp_sample_user.c b/samples/bpf/xdp_sample_user.c index d0b26023f1db..909257ffe54c 100644 --- a/samples/bpf/xdp_sample_user.c +++ b/samples/bpf/xdp_sample_user.c @@ -26,8 +26,10 @@ #define SIOCETHTOOL 0x8946 #endif +#include #include #include +#include #include #include @@ -39,6 +41,7 @@ struct bpf_link *tp_links[NUM_TP] = {}; int map_fds[NUM_MAP], tp_cnt, n_cpus; static int sample_sig_fd; enum log_level sample_log_level = LL_SIMPLE; +static struct sample_output sum_out; static bool err_exp; #define __sample_print(fmt, cond, printer, ...) \ @@ -58,6 +61,9 @@ static bool err_exp; }) #define print_err(err, fmt, ...) __print_err(err, fmt, printf, ##__VA_ARGS__) +#define print_link_err(err, str, width, type) \ + __print_err(err, str, print_link, width, type) + #define __COLUMN(x) "%'10" x " %-13s" #define FMT_COLUMNf __COLUMN(".0f") #define FMT_COLUMNd __COLUMN("d") @@ -71,6 +77,66 @@ static bool err_exp; #define PASS(pass) pass, "pass/s" #define REDIR(redir) redir, "redir/s" +static const char *elixir_search[NUM_TP] = { + [TP_REDIRECT_CNT] = "_trace_xdp_redirect", + [TP_REDIRECT_MAP_CNT] = "_trace_xdp_redirect_map", + [TP_REDIRECT_ERR_CNT] = "_trace_xdp_redirect_err", + [TP_REDIRECT_MAP_ERR_CNT] = "_trace_xdp_redirect_map_err", + [TP_CPUMAP_ENQUEUE_CNT] = "trace_xdp_cpumap_enqueue", + [TP_CPUMAP_KTHREAD_CNT] = "trace_xdp_cpumap_kthread", + [TP_EXCEPTION_CNT] = "trace_xdp_exception", + [TP_DEVMAP_XMIT_CNT] = "trace_xdp_devmap_xmit", +}; + +static const char *make_url(enum tp_type i) +{ + const char *key = elixir_search[i]; + static struct utsname uts = {}; + static char url[128]; + static bool uts_init; + int maj, min; + char c[2]; + + if (!uts_init) { + if (uname(&uts) < 0) + return NULL; + uts_init = true; + } + + if (!key || sscanf(uts.release, "%d.%d%1s", &maj, &min, c) != 3) + return NULL; + + snprintf(url, sizeof(url), "https://elixir.bootlin.com/linux/v%d.%d/C/ident/%s", + maj, min, key); + + return url; +} + +static void print_link(const char *str, int width, enum tp_type i) +{ + static int t = -1; + const char *s; + int fd, l; + + if (t < 0) { + fd = open("/proc/self/fd/1", O_RDONLY); + if (fd < 0) + return; + t = isatty(fd); + close(fd); + } + + s = make_url(i); + if (!s || !t) { + printf(" %-*s", width, str); + return; + } + + l = strlen(str); + width = width - l > 0 ? width - l : 0; + printf(" \x1B]8;;%s\a%s\x1B]8;;\a%*c", s, str, width, ' '); +} + #define NANOSEC_PER_SEC 1000000000 /* 10^9 */ static __u64 gettime(void) { @@ -333,8 +399,11 @@ static void stats_get_cpumap_enqueue(struct stats_record *stats_rec, if (err > 0) err = pps / err; /* calc average bulk size */ - print_default(" %-20s " FMT_COLUMNf FMT_COLUMNf __COLUMN(".2f") "\n", - str, PPS(pps), DROP(drop), err, "bulk_avg"); + + print_link_err(drop, str, 20, TP_CPUMAP_ENQUEUE_CNT); + print_err(drop, + " " FMT_COLUMNf FMT_COLUMNf __COLUMN(".2f") "\n", + PPS(pps), DROP(drop), err, "bulk_avg"); } for (i = 0; i < nr_cpus; i++) { @@ -375,8 +444,9 @@ static void stats_get_cpumap_kthread(struct stats_record *stats_rec, drop = calc_drop_pps(&rec->total, &prev->total, t); err = calc_errs_pps(&rec->total, &prev->total, t); - print_default(" %-20s " FMT_COLUMNf FMT_COLUMNf FMT_COLUMNf "\n", "kthread total", - PPS(pps), DROP(drop), err, "sched"); + print_link_err(drop, pps ? "kthread total" : "kthread", 20, TP_CPUMAP_KTHREAD_CNT); + print_err(drop, " " FMT_COLUMNf FMT_COLUMNf FMT_COLUMNf "\n", + PPS(pps), DROP(drop), err, "sched"); for (i = 0; i < nr_cpus; i++) { struct datarec *r = &rec->cpu[i]; @@ -632,7 +702,9 @@ static void stats_print(const char *prefix, int mask, struct stats_record *r, if (mask & SAMPLE_REDIRECT_CNT) { str = out->redir_cnt.suc ? "redirect total" : "redirect"; - print_default(" %-20s " FMT_COLUMNl "\n", str, REDIR(out->redir_cnt.suc)); + print_link_err(0, str, 20, mask & _SAMPLE_REDIRECT_MAP ? + TP_REDIRECT_MAP_CNT : TP_REDIRECT_CNT); + print_default(" " FMT_COLUMNl "\n", REDIR(out->redir_cnt.suc)); stats_get_redirect_cnt(r, p, nr_cpus, NULL); } @@ -640,6 +712,8 @@ static void stats_print(const char *prefix, int mask, struct stats_record *r, if (mask & SAMPLE_REDIRECT_ERR_CNT) { str = (sample_log_level & LL_DEFAULT) && out->redir_cnt.err ? "redirect_err total" : "redirect_err"; + print_link_err(out->redir_cnt.err, str, 20, mask & _SAMPLE_REDIRECT_MAP ? + TP_REDIRECT_MAP_ERR_CNT : TP_REDIRECT_ERR_CNT); print_err(out->redir_cnt.err, " %-20s " FMT_COLUMNl "\n", str, ERR(out->redir_cnt.err)); @@ -648,8 +722,9 @@ static void stats_print(const char *prefix, int mask, struct stats_record *r, if (mask & SAMPLE_EXCEPTION_CNT) { str = out->except_cnt.hits ? "xdp_exception total" : "xdp_exception"; - print_err(out->except_cnt.hits, " %-20s " FMT_COLUMNl "\n", - str, HITS(out->except_cnt.hits)); + + print_link_err(out->except_cnt.hits, str, 20, TP_EXCEPTION_CNT); + print_err(out->except_cnt.hits, " " FMT_COLUMNl "\n", HITS(out->except_cnt.hits)); stats_get_exception_cnt(r, p, nr_cpus, NULL); } @@ -657,9 +732,11 @@ static void stats_print(const char *prefix, int mask, struct stats_record *r, if (mask & SAMPLE_DEVMAP_XMIT_CNT) { str = (sample_log_level & LL_DEFAULT) && out->xmit_cnt.pps ? "devmap_xmit total" : "devmap_xmit"; + + print_link_err(out->xmit_cnt.err, str, 20, TP_DEVMAP_XMIT_CNT); print_err(out->xmit_cnt.err, - " %-20s " FMT_COLUMNl FMT_COLUMNl FMT_COLUMNl __COLUMN(".2f") "\n", - str, XMIT(out->xmit_cnt.pps), DROP(out->xmit_cnt.drop), + " " FMT_COLUMNl FMT_COLUMNl FMT_COLUMNl __COLUMN(".2f") "\n", + XMIT(out->xmit_cnt.pps), DROP(out->xmit_cnt.drop), out->xmit_cnt.err, "drv_err/s", out->xmit_cnt.bavg, "bulk_avg"); stats_get_devmap_xmit(r, p, nr_cpus, NULL); @@ -747,7 +824,7 @@ void sample_exit(int status) { while (tp_cnt) bpf_link__destroy(tp_links[--tp_cnt]); - + sample_summary_print(); close(sample_sig_fd); exit(status); } @@ -783,8 +860,46 @@ void sample_stats_collect(int mask, struct stats_record *rec) map_collect_percpu(map_fds[DEVMAP_XMIT_CNT], 0, &rec->devmap_xmit); } +void sample_summary_update(struct sample_output *out, int interval) +{ + sum_out.totals.rx += out->totals.rx; + sum_out.totals.redir += out->totals.redir; + sum_out.totals.drop += out->totals.drop; + sum_out.totals.err += out->totals.err; + sum_out.totals.xmit += out->totals.xmit; + sum_out.rx_cnt.pps += interval; +} + +void sample_summary_print(void) +{ + double period = sum_out.rx_cnt.pps; + + print_always("\nTotals\n"); + if (sum_out.totals.rx) { + double pkts = sum_out.totals.rx; + + print_always(" Packets received : %'-10llu\n", sum_out.totals.rx); + print_always(" Average packets/s : %'-10.0f\n", sample_round(pkts/period)); + } + if (sum_out.totals.redir) { + double pkts = sum_out.totals.redir; + + print_always(" Packets redirected : %'-10llu\n", sum_out.totals.redir); + print_always(" Average redir/s : %'-10.0f\n", sample_round(pkts/period)); + } + print_always(" Packets dropped : %'-10llu\n", sum_out.totals.drop); + print_always(" Errors recorded : %'-10llu\n", sum_out.totals.err); + if (sum_out.totals.xmit) { + double pkts = sum_out.totals.xmit; + + print_always(" Packets transmitted : %'-10llu\n", sum_out.totals.xmit); + print_always(" Average transmit/s : %'-10.0f\n", sample_round(pkts/period)); + } +} + void sample_stats_print(int mask, struct stats_record *cur, - struct stats_record *prev, char *prog_name) + struct stats_record *prev, char *prog_name, + int interval) { struct sample_output out = {}; @@ -803,6 +918,8 @@ void sample_stats_print(int mask, struct stats_record *cur, if (mask & SAMPLE_DEVMAP_XMIT_CNT) stats_get_devmap_xmit(cur, prev, 0, &out); + sample_summary_update(&out, interval); + stats_print(prog_name, mask, cur, prev, &out); } @@ -821,7 +938,7 @@ void sample_stats_poll(int interval, int mask, char *prog_name, int use_separato for (;;) { swap(&prev, &record); sample_stats_collect(mask, record); - sample_stats_print(mask, record, prev, prog_name); + sample_stats_print(mask, record, prev, prog_name, interval); fflush(stdout); sleep(interval); sample_reset_mode(); diff --git a/samples/bpf/xdp_sample_user.h b/samples/bpf/xdp_sample_user.h index 6ca934b346ef..abe4ec25c310 100644 --- a/samples/bpf/xdp_sample_user.h +++ b/samples/bpf/xdp_sample_user.h @@ -26,13 +26,16 @@ enum tp_type { }; enum stats_mask { - SAMPLE_RX_CNT = 1U << 1, - SAMPLE_REDIRECT_ERR_CNT = 1U << 2, - SAMPLE_CPUMAP_ENQUEUE_CNT = 1U << 3, - SAMPLE_CPUMAP_KTHREAD_CNT = 1U << 4, - SAMPLE_EXCEPTION_CNT = 1U << 5, - SAMPLE_DEVMAP_XMIT_CNT = 1U << 6, - SAMPLE_REDIRECT_CNT = 1U << 7, + _SAMPLE_REDIRECT_MAP = 1U << 0, + SAMPLE_RX_CNT = 1U << 1, + SAMPLE_REDIRECT_ERR_CNT = 1U << 2, + SAMPLE_CPUMAP_ENQUEUE_CNT = 1U << 3, + SAMPLE_CPUMAP_KTHREAD_CNT = 1U << 4, + SAMPLE_EXCEPTION_CNT = 1U << 5, + SAMPLE_DEVMAP_XMIT_CNT = 1U << 6, + SAMPLE_REDIRECT_CNT = 1U << 7, + SAMPLE_REDIRECT_MAP_CNT = SAMPLE_REDIRECT_CNT | _SAMPLE_REDIRECT_MAP, + SAMPLE_REDIRECT_ERR_MAP_CNT = SAMPLE_REDIRECT_ERR_CNT | _SAMPLE_REDIRECT_MAP, }; static const char *const map_type_strings[] = { @@ -153,8 +156,11 @@ void sample_exit(int status); struct stats_record *alloc_stats_record(void); void free_stats_record(struct stats_record *rec); void sample_stats_print(int mask, struct stats_record *cur, - struct stats_record *prev, char *prog_name); + struct stats_record *prev, char *prog_name, + int interval); void sample_stats_collect(int mask, struct stats_record *rec); +void sample_summary_update(struct sample_output *out, int interval); +void sample_summary_print(void); void sample_stats_poll(int interval, int mask, char *prog_name, int use_separators); void sample_stats_print_cpumap_remote(struct stats_record *stats_rec, From patchwork Fri May 28 23:52:48 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kumar Kartikeya Dwivedi X-Patchwork-Id: 449861 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-15.7 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 6D202C4708D for ; Fri, 28 May 2021 23:54:29 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 4DD116135F for ; Fri, 28 May 2021 23:54:29 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229806AbhE1X4E (ORCPT ); Fri, 28 May 2021 19:56:04 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:45570 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229744AbhE1Xz6 (ORCPT ); Fri, 28 May 2021 19:55:58 -0400 Received: from mail-pg1-x541.google.com (mail-pg1-x541.google.com [IPv6:2607:f8b0:4864:20::541]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 8F200C061574; Fri, 28 May 2021 16:54:22 -0700 (PDT) Received: by mail-pg1-x541.google.com with SMTP id m190so3722592pga.2; Fri, 28 May 2021 16:54:22 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=Lh4cjVXDCTKkenmqi16kX1wwtaby01C381mbKiAGCaw=; b=AHURk11A7mBZ2uA3w3VSsysAccDU/6Jpr5PJVMxIA3nWDGqBM5jVYKbRIar95YGtk+ cOa2x/cGzhIN+klgKIH0T+/wNx1D1WHYfMyulpDa8OSwNISClh08gBUM4Equf5R81G2K PwWMHLADlLaU1Xj0myk4j1GWRHtj5PH5+fg2KbzNMwt4WEGrme9Fp29QEU5KHLWiwmXA JbPKxgQ8zlNjk0QHBitosCrpiJsiImMUmiRjd5LfefHgn2INJ7Wz1+/DUPULANRtmXNv O9knbWAlvX1zw+bfLs70R16yItxXcK7H9ZH+PUV9cwzvFapsKOkFgX52rrNLJR3I9Rjh rnRw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=Lh4cjVXDCTKkenmqi16kX1wwtaby01C381mbKiAGCaw=; b=nyMDAfnvq0M5dROhgz2tuZ/RxN9CqDA8M3/4/6HI8Sh30plAur35XJCY7y6rR8dpkq Sg1y+Tx0emdvvnFLO9TplBg1XnIgGpR1j4mHM5kpcyFhD6d+Hh235wScviWSEIsCDt8k UkjEyjXFjYi89jKgcMDTt8HiYTMOKrsJqrt7AAuIZLECUWXtNBlTLYJOKFsMZWaH1C7f 2STDALL9eLivER6FNvo0i5/FfTRAjgFUR14jcBgybm+cmCKZxXTREUXcnGHpckDuzy+l teTg9nVKqGzQN4Kmqfhfg6rqhAKFgz3D/xn+xV+NzHsR3759drrnlSHm1f3Usc0Qweva q22A== X-Gm-Message-State: AOAM530fX+iUg686LqxXr9s1ZENo+LRyIEhVcRg0HlAJ8ZdE0VSCwmxU jtQwmthSlrS5Po9lRxXC00DQKK/34PE= X-Google-Smtp-Source: ABdhPJxb1UpMs4d1IKn5D8X3U6f3p76MOn7UEzZVxvZsBY0TjmzzZUuRz16mxPQnYDqX1ZipQ834pA== X-Received: by 2002:a63:fc11:: with SMTP id j17mr11207453pgi.355.1622246061765; Fri, 28 May 2021 16:54:21 -0700 (PDT) Received: from localhost ([2402:3a80:11db:3aa9:ad24:a4a2:844f:6a0a]) by smtp.gmail.com with ESMTPSA id o6sm5305091pfb.126.2021.05.28.16.54.20 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 28 May 2021 16:54:21 -0700 (PDT) From: Kumar Kartikeya Dwivedi To: bpf@vger.kernel.org Cc: Kumar Kartikeya Dwivedi , Alexei Starovoitov , Daniel Borkmann , Andrii Nakryiko , Martin KaFai Lau , Song Liu , Yonghong Song , John Fastabend , KP Singh , "David S. Miller" , Jakub Kicinski , Jesper Dangaard Brouer , =?utf-8?q?Toke_H=C3=B8iland-J=C3=B8rgensen?= , netdev@vger.kernel.org Subject: [PATCH RFC bpf-next 13/15] samples: bpf: add new options for xdp samples Date: Sat, 29 May 2021 05:22:48 +0530 Message-Id: <20210528235250.2635167-14-memxor@gmail.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20210528235250.2635167-1-memxor@gmail.com> References: <20210528235250.2635167-1-memxor@gmail.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org These are -i for polling interval and -v for verbose output by default. Some of these tools already supported -s, but we now use that to enable performance impacting success case reporting tracepoint. This is disabled by default, but can be enabled explicitly by user. Use separators (-z) is also dropped. Signed-off-by: Kumar Kartikeya Dwivedi --- samples/bpf/xdp_monitor_user.c | 16 ++++--- samples/bpf/xdp_redirect_cpu_user.c | 41 ++++++++++++----- samples/bpf/xdp_redirect_map_user.c | 71 +++++++++++++++++++++++------ 3 files changed, 96 insertions(+), 32 deletions(-) diff --git a/samples/bpf/xdp_monitor_user.c b/samples/bpf/xdp_monitor_user.c index 73d6d35f0c65..b37d8f7379ec 100644 --- a/samples/bpf/xdp_monitor_user.c +++ b/samples/bpf/xdp_monitor_user.c @@ -38,9 +38,10 @@ struct bpf_object *obj; static const struct option long_options[] = { {"help", no_argument, NULL, 'h' }, {"debug", no_argument, NULL, 'D' }, - {"stats", no_argument, NULL, 'S' }, - {"sec", required_argument, NULL, 's' }, - {0, 0, NULL, 0 } + {"stats", no_argument, NULL, 's' }, + {"interval", required_argument, NULL, 'i' }, + {"verbose", no_argument, NULL, 'v' }, + {} }; static void int_exit(int sig) @@ -121,18 +122,21 @@ int main(int argc, char **argv) int interval = 2; /* Parse commands line args */ - while ((opt = getopt_long(argc, argv, "hDSs:", + while ((opt = getopt_long(argc, argv, "hDi:vs", long_options, &longindex)) != -1) { switch (opt) { case 'D': debug = true; break; - case 'S': + case 's': errors_only = false; break; - case 's': + case 'i': interval = atoi(optarg); break; + case 'v': + sample_log_level ^= LL_DEBUG - 1; + break; case 'h': default: usage(argv); diff --git a/samples/bpf/xdp_redirect_cpu_user.c b/samples/bpf/xdp_redirect_cpu_user.c index 103ac5c24163..d56b89254cd1 100644 --- a/samples/bpf/xdp_redirect_cpu_user.c +++ b/samples/bpf/xdp_redirect_cpu_user.c @@ -42,19 +42,20 @@ static const struct option long_options[] = { {"help", no_argument, NULL, 'h' }, {"dev", required_argument, NULL, 'd' }, {"skb-mode", no_argument, NULL, 'S' }, - {"sec", required_argument, NULL, 's' }, {"progname", required_argument, NULL, 'p' }, {"qsize", required_argument, NULL, 'q' }, {"cpu", required_argument, NULL, 'c' }, {"stress-mode", no_argument, NULL, 'x' }, - {"no-separators", no_argument, NULL, 'z' }, {"force", no_argument, NULL, 'F' }, {"mprog-disable", no_argument, NULL, 'n' }, {"mprog-name", required_argument, NULL, 'e' }, {"mprog-filename", required_argument, NULL, 'f' }, {"redirect-device", required_argument, NULL, 'r' }, {"redirect-map", required_argument, NULL, 'm' }, - {0, 0, NULL, 0 } + {"interval", required_argument, NULL, 'i' }, + {"verbose", no_argument, NULL, 'v' }, + {"stats", no_argument, NULL, 's' }, + {} }; static void int_exit(int sig) @@ -196,7 +197,7 @@ static void stress_cpumap(struct bpf_cpumap_val *value) create_cpu_entry(1, value, 0, false); } -static void __stats_poll(int interval, bool use_separators, char *prog_name, +static void __stats_poll(int interval, bool redir_suc, char *prog_name, char *mprog_name, struct bpf_cpumap_val *value, bool stress_mode) { @@ -210,8 +211,10 @@ static void __stats_poll(int interval, bool use_separators, char *prog_name, sample_stats_collect(mask, record); /* Trick to pretty printf with thousands separators use %' */ - if (use_separators) - setlocale(LC_NUMERIC, "en_US"); + setlocale(LC_NUMERIC, "en_US"); + + if (redir_suc) + mask |= SAMPLE_REDIRECT_CNT; for (;;) { struct timespec ots, nts; @@ -298,12 +301,12 @@ int main(int argc, char **argv) struct bpf_prog_info info = {}; __u32 info_len = sizeof(info); struct bpf_cpumap_val value; - bool use_separators = true; bool stress_mode = false; struct bpf_program *prog; struct bpf_object *obj; int err = EXIT_FAIL; char filename[256]; + bool redir = false; int added_cpus = 0; int longindex = 0; int interval = 2; @@ -356,7 +359,7 @@ int main(int argc, char **argv) memset(cpu, 0, n_cpus * sizeof(int)); /* Parse commands line args */ - while ((opt = getopt_long(argc, argv, "hSd:s:p:q:c:xzFf:e:r:m:", + while ((opt = getopt_long(argc, argv, "hSd:sp:q:c:xi:vFf:e:r:m:", long_options, &longindex)) != -1) { switch (opt) { case 'd': @@ -375,6 +378,9 @@ int main(int argc, char **argv) } break; case 's': + redir = true; + break; + case 'i': interval = atoi(optarg); break; case 'S': @@ -383,9 +389,6 @@ int main(int argc, char **argv) case 'x': stress_mode = true; break; - case 'z': - use_separators = false; - break; case 'p': /* Selecting eBPF prog to load */ prog_name = optarg; @@ -422,6 +425,9 @@ int main(int argc, char **argv) case 'F': xdp_flags &= ~XDP_FLAGS_UPDATE_IF_NOEXIST; break; + case 'v': + sample_log_level ^= LL_DEBUG - 1; + break; case 'h': error: default: @@ -492,7 +498,18 @@ int main(int argc, char **argv) } prog_id = info.id; - __stats_poll(interval, use_separators, prog_name, mprog_name, + if (!redir) { + /* The bpf_link[i] depend on the order of + * the functions was defined in _kern.c + */ + bpf_link__destroy(tp_links[2]); /* tracepoint/xdp/xdp_redirect */ + tp_links[2] = NULL; + + bpf_link__destroy(tp_links[3]); /* tracepoint/xdp/xdp_redirect_map */ + tp_links[3] = NULL; + } + + __stats_poll(interval, redir, prog_name, mprog_name, &value, stress_mode); err = EXIT_OK; diff --git a/samples/bpf/xdp_redirect_map_user.c b/samples/bpf/xdp_redirect_map_user.c index ed53dd2cd93a..eb4013fa58cb 100644 --- a/samples/bpf/xdp_redirect_map_user.c +++ b/samples/bpf/xdp_redirect_map_user.c @@ -13,6 +13,7 @@ #include #include #include +#include #include "bpf_util.h" #include @@ -28,6 +29,18 @@ static __u32 dummy_prog_id; static __u32 xdp_flags = XDP_FLAGS_UPDATE_IF_NOEXIST; +static const struct option long_options[] = { + {"help", no_argument, NULL, 'h' }, + {"skb-mode", no_argument, NULL, 'S' }, + {"native-mode", no_argument, NULL, 'N' }, + {"force", no_argument, NULL, 'F' }, + {"load-egress", no_argument, NULL, 'X' }, + {"stats", no_argument, NULL, 's' }, + {"interval", required_argument, NULL, 'i' }, + {"verbose", no_argument, NULL, 'v' }, + {} +}; + static void int_exit(int sig) { __u32 curr_prog_id = 0; @@ -61,16 +74,25 @@ static void int_exit(int sig) sample_exit(EXIT_OK); } -static void usage(const char *prog) +static void usage(char *argv[]) { - fprintf(stderr, - "usage: %s [OPTS] _IN _OUT\n\n" - "OPTS:\n" - " -S use skb-mode\n" - " -N enforce native mode\n" - " -F force loading prog\n" - " -X load xdp program on egress\n", - prog); + int i; + + printf("\n"); + printf(" Usage: %s (options-see-below)\n", + argv[0]); + printf(" Listing options:\n"); + for (i = 0; long_options[i].name != 0; i++) { + printf(" --%-15s", long_options[i].name); + if (long_options[i].flag != NULL) + printf(" flag (internal value:%d)", + *long_options[i].flag); + else + printf("short-option: -%c", + long_options[i].val); + printf("\n"); + } + printf("\n"); } int main(int argc, char **argv) @@ -88,13 +110,14 @@ int main(int argc, char **argv) char str[2 * IF_NAMESIZE + 1]; __u32 info_len = sizeof(info); char ifname_out[IF_NAMESIZE]; - const char *optstr = "FSNX"; char ifname_in[IF_NAMESIZE]; struct bpf_object *obj; int ret, opt, key = 0; char filename[256]; + int interval = 2; - while ((opt = getopt(argc, argv, optstr)) != -1) { + while ((opt = getopt_long(argc, argv, "FSNXi:vs", + long_options, NULL)) != -1) { switch (opt) { case 'S': xdp_flags |= XDP_FLAGS_SKB_MODE; @@ -108,8 +131,17 @@ int main(int argc, char **argv) case 'X': xdp_devmap_attached = true; break; + case 'i': + interval = atoi(optarg); + break; + case 'v': + sample_log_level ^= LL_DEBUG - 1; + break; + case 's': + mask |= SAMPLE_REDIRECT_MAP_CNT; + break; default: - usage(basename(argv[0])); + usage(argv); return 1; } } @@ -122,7 +154,7 @@ int main(int argc, char **argv) } if (argc <= optind + 1) { - usage(basename(argv[0])); + usage(argv); return 1; } @@ -252,9 +284,20 @@ int main(int argc, char **argv) ifname_in, ifindex_in, str, ifname_out, ifindex_out, get_driver_name(ifindex_out) ?: "(err)"); + if ((mask & SAMPLE_REDIRECT_CNT) == 0) { + /* The bpf_link[i] depend on the order of + * the functions was defined in _kern.c + */ + bpf_link__destroy(tp_links[2]); /* tracepoint/xdp/xdp_redirect */ + tp_links[2] = NULL; + + bpf_link__destroy(tp_links[3]); /* tracepoint/xdp/xdp_redirect_map */ + tp_links[3] = NULL; + } + snprintf(str, sizeof(str), "%s->%s", ifname_in, ifname_out); - sample_stats_poll(1, mask, str, true); + sample_stats_poll(interval, mask, str, true); return 0; From patchwork Fri May 28 23:52:50 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kumar Kartikeya Dwivedi X-Patchwork-Id: 449860 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-15.7 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id E8E5BC4708F for ; Fri, 28 May 2021 23:54:38 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id CF281613B4 for ; Fri, 28 May 2021 23:54:38 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229791AbhE1X4M (ORCPT ); Fri, 28 May 2021 19:56:12 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:45614 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229783AbhE1X4G (ORCPT ); Fri, 28 May 2021 19:56:06 -0400 Received: from mail-pj1-x1042.google.com (mail-pj1-x1042.google.com [IPv6:2607:f8b0:4864:20::1042]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 5E5B9C06138A; Fri, 28 May 2021 16:54:29 -0700 (PDT) Received: by mail-pj1-x1042.google.com with SMTP id lx17-20020a17090b4b11b029015f3b32b8dbso5477487pjb.0; Fri, 28 May 2021 16:54:29 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=mQVWnl5kD4VZJGsvupF6sFLlOwXDd/uH9jRxPkLWhRE=; b=DCKCEUaXO3M7SuyK3CFkRo4p0+FRQ8EOSfNdca7pm87L4NPtZaF3AjrdIXTmAhD7aR cqQFfxT5QlETKevwgEcueirhu5sjGFhGV7PXHqP5ITCoEYYr3oUoqmmKKjtc3iwnJvMc 6IndgMeFw3+0VQhr0xqajANXhONBbIYqPumRRgwRy5wHJ/nEJINn2a5tUM5QaGB0AZvt k8tXjEJuEF/qXrq6YmwPjyrxwddu0jCur2UTo3KZ1IhDGuEEpxOOUQgoiD2dFxPxVxPN K+QCSJJyngS31TFALN2jBeb6+B5bT4MIrIMQ6zAVqf5HshlTZT4ps7xx2GfyP1aAfFKf 6zig== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=mQVWnl5kD4VZJGsvupF6sFLlOwXDd/uH9jRxPkLWhRE=; b=VX/K18Qh1PV0HUKnysnqpMkwQ2xjXuX6LtG6OWUPFMr8qgKL5nwuhB+/aZT6bXgk0c 4J3AsZs4sv//GIzwWsLz9aTZzkM+mr03HYemCF9pmCRnTKJDyTsFWG19VdYeLeVZiwiJ 0FyuwLoKJgcWR2nLKi1Lp8JmTwr/3vmcjeQDgYjfZ3wVTioeT3Q/z+2ViFpgiwAFkIT4 f9hLWu8y4xpiwtuUQlaZrOskAJpPIz++lptHYfFoYvXxRslMT36YmbG2+br3sZExn/9P AX+1XZW8fmWsHAP7ND4UKsh4qIYHDVESNPxMcoJCU/DrzZKiNju5yeUja3lHgsrzmzLj dFrg== X-Gm-Message-State: AOAM532qFLeEmLoUTtnSFgATb4SYwbPq5Y8iviMVI/bQihlLWAUwjIv/ LSPFZUPLVKa0fMixbBkjrNCQcgzbAuY= X-Google-Smtp-Source: ABdhPJz4Pa7mqTfr3xzapFUEmmX1JtoVd4K49xhXmYURDfEzACYU80QgQhSwpzYwqjfpHj9a2khXHQ== X-Received: by 2002:a17:903:228a:b029:f7:9f7e:aa2c with SMTP id b10-20020a170903228ab02900f79f7eaa2cmr10167345plh.71.1622246068663; Fri, 28 May 2021 16:54:28 -0700 (PDT) Received: from localhost ([2402:3a80:11db:3aa9:ad24:a4a2:844f:6a0a]) by smtp.gmail.com with ESMTPSA id f186sm5382410pfb.36.2021.05.28.16.54.27 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 28 May 2021 16:54:28 -0700 (PDT) From: Kumar Kartikeya Dwivedi To: bpf@vger.kernel.org Cc: Kumar Kartikeya Dwivedi , Alexei Starovoitov , Daniel Borkmann , Andrii Nakryiko , Martin KaFai Lau , Song Liu , Yonghong Song , John Fastabend , KP Singh , "David S. Miller" , Jakub Kicinski , Jesper Dangaard Brouer , =?utf-8?q?Toke_H=C3=B8iland-J=C3=B8rgensen?= , netdev@vger.kernel.org Subject: [PATCH RFC bpf-next 15/15] samples: bpf: convert xdp_samples to use raw_tracepoints Date: Sat, 29 May 2021 05:22:50 +0530 Message-Id: <20210528235250.2635167-16-memxor@gmail.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20210528235250.2635167-1-memxor@gmail.com> References: <20210528235250.2635167-1-memxor@gmail.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org These are faster, and hence speeds up cases where user passes --stats to enable success case redirect accounting. We can extend this to all other tracepoints as well, so make that part of this change. Signed-off-by: Kumar Kartikeya Dwivedi --- samples/bpf/xdp_sample_kern.h | 145 +++++++++++----------------------- samples/bpf/xdp_sample_user.c | 2 +- 2 files changed, 45 insertions(+), 102 deletions(-) diff --git a/samples/bpf/xdp_sample_kern.h b/samples/bpf/xdp_sample_kern.h index dd7f7ea63166..08fbc55df3fd 100644 --- a/samples/bpf/xdp_sample_kern.h +++ b/samples/bpf/xdp_sample_kern.h @@ -3,6 +3,9 @@ #pragma once #include +#include +#include +#include #include #ifndef NR_CPUS @@ -85,20 +88,6 @@ struct { /*** Trace point code ***/ -/* Tracepoint format: /sys/kernel/debug/tracing/events/xdp/xdp_redirect/format - * Code in: kernel/include/trace/events/xdp.h - */ -struct xdp_redirect_ctx { - u64 __pad; // First 8 bytes are not accessible by bpf code - int prog_id; // offset:8; size:4; signed:1; - u32 act; // offset:12 size:4; signed:0; - int ifindex; // offset:16 size:4; signed:1; - int err; // offset:20 size:4; signed:1; - int to_ifindex; // offset:24 size:4; signed:1; - u32 map_id; // offset:28 size:4; signed:0; - int map_index; // offset:32 size:4; signed:1; -}; // offset:36 - enum { XDP_REDIRECT_SUCCESS = 0, XDP_REDIRECT_ERROR = 1 @@ -124,11 +113,11 @@ __u32 xdp_get_err_key(int err) } static __always_inline -int xdp_redirect_collect_stat(struct xdp_redirect_ctx *ctx) +int xdp_redirect_collect_stat(struct bpf_raw_tracepoint_args *ctx) { u32 key = XDP_REDIRECT_ERROR; + int err = ctx->args[3]; struct datarec *rec; - int err = ctx->err; key = xdp_get_err_key(err); @@ -149,47 +138,35 @@ int xdp_redirect_collect_stat(struct xdp_redirect_ctx *ctx) */ } -SEC("tracepoint/xdp/xdp_redirect_err") -int trace_xdp_redirect_err(struct xdp_redirect_ctx *ctx) +SEC("raw_tracepoint/xdp_redirect_err") +int trace_xdp_redirect_err(struct bpf_raw_tracepoint_args *ctx) { return xdp_redirect_collect_stat(ctx); } -SEC("tracepoint/xdp/xdp_redirect_map_err") -int trace_xdp_redirect_map_err(struct xdp_redirect_ctx *ctx) +SEC("raw_tracepoint/xdp_redirect_map_err") +int trace_xdp_redirect_map_err(struct bpf_raw_tracepoint_args *ctx) { return xdp_redirect_collect_stat(ctx); } -/* Likely unloaded when prog starts */ -SEC("tracepoint/xdp/xdp_redirect") -int trace_xdp_redirect(struct xdp_redirect_ctx *ctx) +SEC("raw_tracepoint/xdp_redirect") +int trace_xdp_redirect(struct bpf_raw_tracepoint_args *ctx) { return xdp_redirect_collect_stat(ctx); } -/* Likely unloaded when prog starts */ -SEC("tracepoint/xdp/xdp_redirect_map") -int trace_xdp_redirect_map(struct xdp_redirect_ctx *ctx) +SEC("raw_tracepoint/xdp_redirect_map") +int trace_xdp_redirect_map(struct bpf_raw_tracepoint_args *ctx) { return xdp_redirect_collect_stat(ctx); } -/* Tracepoint format: /sys/kernel/debug/tracing/events/xdp/xdp_exception/format - * Code in: kernel/include/trace/events/xdp.h - */ -struct xdp_exception_ctx { - u64 __pad; // First 8 bytes are not accessible by bpf code - int prog_id; // offset:8; size:4; signed:1; - u32 act; // offset:12; size:4; signed:0; - int ifindex; // offset:16; size:4; signed:1; -}; - -SEC("tracepoint/xdp/xdp_exception") -int trace_xdp_exception(struct xdp_exception_ctx *ctx) +SEC("raw_tracepoint/xdp_exception") +int trace_xdp_exception(struct bpf_raw_tracepoint_args *ctx) { + u32 key = ctx->args[2]; struct datarec *rec; - u32 key = ctx->act; if (key > XDP_REDIRECT) key = XDP_UNKNOWN; @@ -202,23 +179,10 @@ int trace_xdp_exception(struct xdp_exception_ctx *ctx) return 0; } -/* Tracepoint: /sys/kernel/debug/tracing/events/xdp/xdp_cpumap_enqueue/format - * Code in: kernel/include/trace/events/xdp.h - */ -struct cpumap_enqueue_ctx { - u64 __pad; // First 8 bytes are not accessible by bpf code - int map_id; // offset:8; size:4; signed:1; - u32 act; // offset:12; size:4; signed:0; - int cpu; // offset:16; size:4; signed:1; - unsigned int drops; // offset:20; size:4; signed:0; - unsigned int processed; // offset:24; size:4; signed:0; - int to_cpu; // offset:28; size:4; signed:1; -}; - -SEC("tracepoint/xdp/xdp_cpumap_enqueue") -int trace_xdp_cpumap_enqueue(struct cpumap_enqueue_ctx *ctx) +SEC("raw_tracepoint/xdp_cpumap_enqueue") +int trace_xdp_cpumap_enqueue(struct bpf_raw_tracepoint_args *ctx) { - u32 to_cpu = ctx->to_cpu; + u32 to_cpu = ctx->args[3]; struct datarec *rec; if (to_cpu >= MAX_CPUS) @@ -227,11 +191,11 @@ int trace_xdp_cpumap_enqueue(struct cpumap_enqueue_ctx *ctx) rec = bpf_map_lookup_elem(&cpumap_enqueue_cnt, &to_cpu); if (!rec) return 0; - rec->processed += ctx->processed; - rec->dropped += ctx->drops; + rec->processed += ctx->args[1]; + rec->dropped += ctx->args[2]; /* Record bulk events, then userspace can calc average bulk size */ - if (ctx->processed > 0) + if (ctx->args[1] > 0) rec->issue += 1; /* Inception: It's possible to detect overload situations, via @@ -242,78 +206,57 @@ int trace_xdp_cpumap_enqueue(struct cpumap_enqueue_ctx *ctx) return 0; } -/* Tracepoint: /sys/kernel/debug/tracing/events/xdp/xdp_cpumap_kthread/format - * Code in: kernel/include/trace/events/xdp.h - */ -struct cpumap_kthread_ctx { - u64 __pad; // First 8 bytes are not accessible - int map_id; // offset:8; size:4; signed:1; - u32 act; // offset:12; size:4; signed:0; - int cpu; // offset:16; size:4; signed:1; - unsigned int drops; // offset:20; size:4; signed:0; - unsigned int processed; // offset:24; size:4; signed:0; - int sched; // offset:28; size:4; signed:1; - unsigned int xdp_pass; // offset:32; size:4; signed:0; - unsigned int xdp_drop; // offset:36; size:4; signed:0; - unsigned int xdp_redirect; // offset:40; size:4; signed:0; -}; - -SEC("tracepoint/xdp/xdp_cpumap_kthread") -int trace_xdp_cpumap_kthread(struct cpumap_kthread_ctx *ctx) +SEC("raw_tracepoint/xdp_cpumap_kthread") +int trace_xdp_cpumap_kthread(struct bpf_raw_tracepoint_args *ctx) { + struct xdp_cpumap_stats *stats; struct datarec *rec; u32 key = 0; + stats = (struct xdp_cpumap_stats *) ctx->args[4]; + if (!stats) + return 0; + rec = bpf_map_lookup_elem(&cpumap_kthread_cnt, &key); if (!rec) return 0; - rec->processed += ctx->processed; - rec->dropped += ctx->drops; - rec->xdp_pass += ctx->xdp_pass; - rec->xdp_drop += ctx->xdp_drop; - rec->xdp_redirect += ctx->xdp_redirect; + rec->processed += ctx->args[1]; + rec->dropped += ctx->args[2]; + + rec->xdp_pass += BPF_CORE_READ(stats, pass); + rec->xdp_drop += BPF_CORE_READ(stats, drop); + rec->xdp_redirect += BPF_CORE_READ(stats, redirect); /* Count times kthread yielded CPU via schedule call */ - if (ctx->sched) + if (ctx->args[3]) rec->issue++; return 0; } -/* Tracepoint: /sys/kernel/debug/tracing/events/xdp/xdp_devmap_xmit/format - * Code in: kernel/include/trace/events/xdp.h - */ -struct devmap_xmit_ctx { - u64 __pad; // First 8 bytes are not accessible by bpf code - int from_ifindex; // offset:8; size:4; signed:1; - u32 act; // offset:12; size:4; signed:0; - int to_ifindex; // offset:16; size:4; signed:1; - int drops; // offset:20; size:4; signed:1; - int sent; // offset:24; size:4; signed:1; - int err; // offset:28; size:4; signed:1; -}; - -SEC("tracepoint/xdp/xdp_devmap_xmit") -int trace_xdp_devmap_xmit(struct devmap_xmit_ctx *ctx) +SEC("raw_tracepoint/xdp_devmap_xmit") +int trace_xdp_devmap_xmit(struct bpf_raw_tracepoint_args *ctx) { struct datarec *rec; u32 key = 0; + int drops; rec = bpf_map_lookup_elem(&devmap_xmit_cnt, &key); if (!rec) return 0; - rec->processed += ctx->sent; - rec->dropped += ctx->drops; + rec->processed += ctx->args[2]; + rec->dropped += ctx->args[3]; /* Record bulk events, then userspace can calc average bulk size */ rec->info += 1; /* Record error cases, where no frame were sent */ - if (ctx->err) + if (ctx->args[4]) rec->issue++; + drops = ctx->args[3]; /* Catch API error of drv ndo_xdp_xmit sent more than count */ - if (ctx->drops < 0) + if (drops < 0) rec->issue++; return 1; diff --git a/samples/bpf/xdp_sample_user.c b/samples/bpf/xdp_sample_user.c index aa02d9bbea6c..539c0c78fcb0 100644 --- a/samples/bpf/xdp_sample_user.c +++ b/samples/bpf/xdp_sample_user.c @@ -805,7 +805,7 @@ static int init_tracepoints(struct bpf_object *obj) struct bpf_program *prog; bpf_object__for_each_program(prog, obj) { - if (bpf_program__is_tracepoint(prog) != true) + if (!bpf_program__is_raw_tracepoint(prog)) continue; tp_links[tp_cnt] = bpf_program__attach(prog);