From: Song Liu <songliubraving@fb.com> To: Andrii Nakryiko <andrii.nakryiko@gmail.com> Cc: bpf <bpf@vger.kernel.org>, Networking <netdev@vger.kernel.org>, open list <linux-kernel@vger.kernel.org>, Alexei Starovoitov <ast@kernel.org>, "Daniel Borkmann" <daniel@iogearbox.net>, Kernel Team <Kernel-team@fb.com>, "Peter Ziljstra" <peterz@infradead.org> Subject: Re: [PATCH v4 bpf-next 2/6] bpf: prevent deadlock from recursive bpf_task_storage_[get|delete] Date: Tue, 23 Feb 2021 07:16:18 +0000 Message-ID: <6A4F1927-AF73-4AC8-AE44-5878ACEDF944@fb.com> (raw) In-Reply-To: <CAEf4BzaZ0ATbJsLoQu_SRUYgzkak9zv61N+T=gijOQ+X=57ErA@mail.gmail.com> > On Feb 22, 2021, at 10:21 PM, Andrii Nakryiko <andrii.nakryiko@gmail.com> wrote: > > On Mon, Feb 22, 2021 at 5:23 PM Song Liu <songliubraving@fb.com> wrote: >> >> BPF helpers bpf_task_storage_[get|delete] could hold two locks: >> bpf_local_storage_map_bucket->lock and bpf_local_storage->lock. Calling >> these helpers from fentry/fexit programs on functions in bpf_*_storage.c >> may cause deadlock on either locks. >> >> Prevent such deadlock with a per cpu counter, bpf_task_storage_busy, which >> is similar to bpf_prog_active. We need this counter to be global, because >> the two locks here belong to two different objects: bpf_local_storage_map >> and bpf_local_storage. If we pick one of them as the owner of the counter, >> it is still possible to trigger deadlock on the other lock. For example, >> if bpf_local_storage_map owns the counters, it cannot prevent deadlock >> on bpf_local_storage->lock when two maps are used. >> >> Signed-off-by: Song Liu <songliubraving@fb.com> >> --- >> kernel/bpf/bpf_task_storage.c | 57 ++++++++++++++++++++++++++++++----- >> 1 file changed, 50 insertions(+), 7 deletions(-) >> > > [...] > >> @@ -109,7 +136,9 @@ static void *bpf_pid_task_storage_lookup_elem(struct bpf_map *map, void *key) >> goto out; >> } >> >> + bpf_task_storage_lock(); >> sdata = task_storage_lookup(task, map, true); >> + bpf_task_storage_unlock(); >> put_pid(pid); >> return sdata ? sdata->data : NULL; >> out: >> @@ -141,8 +170,10 @@ static int bpf_pid_task_storage_update_elem(struct bpf_map *map, void *key, >> goto out; >> } >> >> + bpf_task_storage_lock(); >> sdata = bpf_local_storage_update( >> task, (struct bpf_local_storage_map *)map, value, map_flags); > > this should probably be container_of() instead of casting bpf_task_storage.c uses casting in multiple places. How about we fix it in a separate patch? Thanks, Song > >> + bpf_task_storage_unlock(); >> >> err = PTR_ERR_OR_ZERO(sdata); >> out: >> @@ -185,7 +216,9 @@ static int bpf_pid_task_storage_delete_elem(struct bpf_map *map, void *key) >> goto out; >> } >> >> + bpf_task_storage_lock(); >> err = task_storage_delete(task, map); >> + bpf_task_storage_unlock(); >> out: >> put_pid(pid); >> return err; > > [...]
next prev parent reply index Thread overview: 20+ messages / expand[flat|nested] mbox.gz Atom feed top 2021-02-23 1:20 [PATCH v4 bpf-next 0/6] bpf: enable task local storage for tracing programs Song Liu 2021-02-23 1:20 ` [PATCH v4 bpf-next 1/6] " Song Liu 2021-02-23 3:08 ` kernel test robot 2021-02-23 4:04 ` kernel test robot 2021-02-23 19:23 ` Martin KaFai Lau 2021-02-23 20:51 ` Song Liu 2021-02-23 1:20 ` [PATCH v4 bpf-next 2/6] bpf: prevent deadlock from recursive bpf_task_storage_[get|delete] Song Liu 2021-02-23 6:21 ` Andrii Nakryiko 2021-02-23 7:16 ` Song Liu [this message] 2021-02-23 7:19 ` Andrii Nakryiko 2021-02-23 16:44 ` Alexei Starovoitov 2021-02-23 11:06 ` Peter Zijlstra 2021-02-23 20:49 ` Song Liu 2021-02-23 1:20 ` [PATCH v4 bpf-next 3/6] selftests/bpf: add non-BPF_LSM test for task local storage Song Liu 2021-02-23 1:20 ` [PATCH v4 bpf-next 4/6] selftests/bpf: test deadlock from recursive bpf_task_storage_[get|delete] Song Liu 2021-02-23 1:20 ` [PATCH v4 bpf-next 5/6] bpf: runqslower: prefer using local vmlimux to generate vmlinux.h Song Liu 2021-02-23 6:26 ` Andrii Nakryiko 2021-02-23 21:24 ` Martin KaFai Lau 2021-02-23 1:20 ` [PATCH v4 bpf-next 6/6] bpf: runqslower: use task local storage Song Liu 2021-02-23 21:33 ` Martin KaFai Lau
Reply instructions: You may reply publicly to this message via plain-text email using any one of the following methods: * Save the following mbox file, import it into your mail client, and reply-to-all from there: mbox Avoid top-posting and favor interleaved quoting: https://en.wikipedia.org/wiki/Posting_style#Interleaved_style * Reply using the --to, --cc, and --in-reply-to switches of git-send-email(1): git send-email \ --in-reply-to=6A4F1927-AF73-4AC8-AE44-5878ACEDF944@fb.com \ --to=songliubraving@fb.com \ --cc=Kernel-team@fb.com \ --cc=andrii.nakryiko@gmail.com \ --cc=ast@kernel.org \ --cc=bpf@vger.kernel.org \ --cc=daniel@iogearbox.net \ --cc=linux-kernel@vger.kernel.org \ --cc=netdev@vger.kernel.org \ --cc=peterz@infradead.org \ /path/to/YOUR_REPLY https://kernel.org/pub/software/scm/git/docs/git-send-email.html * If your mail client supports setting the In-Reply-To header via mailto: links, try the mailto: link
BPF Archive on lore.kernel.org Archives are clonable: git clone --mirror https://lore.kernel.org/bpf/0 bpf/git/0.git # If you have public-inbox 1.1+ installed, you may # initialize and index your mirror using the following commands: public-inbox-init -V2 bpf bpf/ https://lore.kernel.org/bpf \ bpf@vger.kernel.org public-inbox-index bpf Example config snippet for mirrors Newsgroup available over NNTP: nntp://nntp.lore.kernel.org/org.kernel.vger.bpf AGPL code for this site: git clone https://public-inbox.org/public-inbox.git