€•8eŒsphinx.addnodes”Œdocument”“”)”}”(Œ rawsource”Œ”Œchildren”]”(Œ translations”Œ LanguagesNode”“”)”}”(hhh]”(hŒ pending_xref”“”)”}”(hhh]”Œdocutils.nodes”ŒText”“”ŒChinese (Simplified)”…””}”Œparent”hsbaŒ attributes”}”(Œids”]”Œclasses”]”Œnames”]”Œdupnames”]”Œbackrefs”]”Œ refdomain”Œstd”Œreftype”Œdoc”Œ reftarget”Œ /translations/zh_CN/bpf/prog_lsm”Œmodname”NŒ classname”NŒ refexplicit”ˆuŒtagname”hhh ubh)”}”(hhh]”hŒChinese (Traditional)”…””}”hh2sbah}”(h]”h ]”h"]”h$]”h&]”Œ refdomain”h)Œreftype”h+Œ reftarget”Œ /translations/zh_TW/bpf/prog_lsm”Œmodname”NŒ classname”NŒ refexplicit”ˆuh1hhh ubh)”}”(hhh]”hŒItalian”…””}”hhFsbah}”(h]”h ]”h"]”h$]”h&]”Œ refdomain”h)Œreftype”h+Œ reftarget”Œ /translations/it_IT/bpf/prog_lsm”Œmodname”NŒ classname”NŒ refexplicit”ˆuh1hhh ubh)”}”(hhh]”hŒJapanese”…””}”hhZsbah}”(h]”h ]”h"]”h$]”h&]”Œ refdomain”h)Œreftype”h+Œ reftarget”Œ /translations/ja_JP/bpf/prog_lsm”Œmodname”NŒ classname”NŒ refexplicit”ˆuh1hhh ubh)”}”(hhh]”hŒKorean”…””}”hhnsbah}”(h]”h ]”h"]”h$]”h&]”Œ refdomain”h)Œreftype”h+Œ reftarget”Œ /translations/ko_KR/bpf/prog_lsm”Œmodname”NŒ classname”NŒ refexplicit”ˆuh1hhh ubh)”}”(hhh]”hŒPortuguese (Brazilian)”…””}”hh‚sbah}”(h]”h ]”h"]”h$]”h&]”Œ refdomain”h)Œreftype”h+Œ reftarget”Œ /translations/pt_BR/bpf/prog_lsm”Œmodname”NŒ classname”NŒ refexplicit”ˆuh1hhh ubh)”}”(hhh]”hŒSpanish”…””}”hh–sbah}”(h]”h ]”h"]”h$]”h&]”Œ refdomain”h)Œreftype”h+Œ reftarget”Œ /translations/sp_SP/bpf/prog_lsm”Œmodname”NŒ classname”NŒ refexplicit”ˆuh1hhh ubeh}”(h]”h ]”h"]”h$]”h&]”Œcurrent_language”ŒEnglish”uh1h hhŒ _document”hŒsource”NŒline”NubhŒcomment”“”)”}”(hŒ!SPDX-License-Identifier: GPL-2.0+”h]”hŒ!SPDX-License-Identifier: GPL-2.0+”…””}”hh·sbah}”(h]”h ]”h"]”h$]”h&]”Œ xml:space”Œpreserve”uh1hµhhh²hh³Œ:/var/lib/git/docbuild/linux/Documentation/bpf/prog_lsm.rst”h´Kubh¶)”}”(hŒCopyright (C) 2020 Google LLC.”h]”hŒCopyright (C) 2020 Google LLC.”…””}”hhÈsbah}”(h]”h ]”h"]”h$]”h&]”hÅhÆuh1hµhhh²hh³hÇh´KubhŒsection”“”)”}”(hhh]”(hŒtitle”“”)”}”(hŒLSM BPF Programs”h]”hŒLSM BPF Programs”…””}”(hhÝh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1hÛhhØh²hh³hÇh´KubhŒ paragraph”“”)”}”(hŒ¬These BPF programs allow runtime instrumentation of the LSM hooks by privileged users to implement system-wide MAC (Mandatory Access Control) and Audit policies using eBPF.”h]”hŒ¬These BPF programs allow runtime instrumentation of the LSM hooks by privileged users to implement system-wide MAC (Mandatory Access Control) and Audit policies using eBPF.”…””}”(hhíh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´KhhØh²hubh×)”}”(hhh]”(hÜ)”}”(hŒ Structure”h]”hŒ Structure”…””}”(hhþh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1hÛhhûh²hh³hÇh´K ubhì)”}”(hŒYThe example shows an eBPF program that can be attached to the ``file_mprotect`` LSM hook:”h]”(hŒ>The example shows an eBPF program that can be attached to the ”…””}”(hj h²hh³Nh´NubhŒliteral”“”)”}”(hŒ``file_mprotect``”h]”hŒ file_mprotect”…””}”(hjh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhj ubhŒ LSM hook:”…””}”(hj h²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´Khhûh²hubhŒindex”“”)”}”(hhh]”h}”(h]”h ]”h"]”h$]”h&]”Œentries”]”(Œsingle”Œfile_mprotect (C function)”Œc.file_mprotect”hNt”auh1j.hhûh²hh³Nh´NubhŒdesc”“”)”}”(hhh]”(hŒdesc_signature”“”)”}”(hŒYint file_mprotect(struct vm_area_struct *vma, unsigned long reqprot, unsigned long prot);”h]”hŒdesc_signature_line”“”)”}”(hŒYint file_mprotect(struct vm_area_struct *vma, unsigned long reqprot, unsigned long prot);”h]”(hŒdesc_sig_keyword_type”“”)”}”(hŒint”h]”hŒint”…””}”(hjRh²hh³Nh´Nubah}”(h]”h ]”Œkt”ah"]”h$]”h&]”uh1jPhjLh²hh³hÇh´KubhŒdesc_sig_space”“”)”}”(hŒ ”h]”hŒ ”…””}”(hjch²hh³Nh´Nubah}”(h]”h ]”Œw”ah"]”h$]”h&]”uh1jahjLh²hh³hÇh´KubhŒ desc_name”“”)”}”(hŒ file_mprotect”h]”hŒ desc_sig_name”“”)”}”(hŒ file_mprotect”h]”hŒ file_mprotect”…””}”(hjzh²hh³Nh´Nubah}”(h]”h ]”Œn”ah"]”h$]”h&]”uh1jxhjtubah}”(h]”h ]”(Œsig-name”Œdescname”eh"]”h$]”h&]”hÅhÆuh1jrhjLh²hh³hÇh´KubhŒdesc_parameterlist”“”)”}”(hŒG(struct vm_area_struct *vma, unsigned long reqprot, unsigned long prot)”h]”(hŒdesc_parameter”“”)”}”(hŒstruct vm_area_struct *vma”h]”(hŒdesc_sig_keyword”“”)”}”(hŒstruct”h]”hŒstruct”…””}”(hjŸh²hh³Nh´Nubah}”(h]”h ]”Œk”ah"]”h$]”h&]”uh1jhj™ubjb)”}”(hŒ ”h]”hŒ ”…””}”(hj®h²hh³Nh´Nubah}”(h]”h ]”jnah"]”h$]”h&]”uh1jahj™ubh)”}”(hhh]”jy)”}”(hŒvm_area_struct”h]”hŒvm_area_struct”…””}”(hj¿h²hh³Nh´Nubah}”(h]”h ]”j…ah"]”h$]”h&]”uh1jxhj¼ubah}”(h]”h ]”h"]”h$]”h&]”Œ refdomain”Œc”Œreftype”Œ identifier”Œ reftarget”jÁŒmodname”NŒ classname”NŒ c:parent_key”Œsphinx.domains.c”Œ LookupKey”“”)”}”Œdata”]”jÛŒ ASTIdentifier”“”)”}”jÖj|sbŒc.file_mprotect”†”asbuh1hhj™ubjb)”}”(hŒ ”h]”hŒ ”…””}”(hjèh²hh³Nh´Nubah}”(h]”h ]”jnah"]”h$]”h&]”uh1jahj™ubhŒdesc_sig_punctuation”“”)”}”(hŒ*”h]”hŒ*”…””}”(hjøh²hh³Nh´Nubah}”(h]”h ]”Œp”ah"]”h$]”h&]”uh1jöhj™ubjy)”}”(hŒvma”h]”hŒvma”…””}”(hjh²hh³Nh´Nubah}”(h]”h ]”j…ah"]”h$]”h&]”uh1jxhj™ubeh}”(h]”h ]”h"]”h$]”h&]”Œnoemph”ˆhÅhÆuh1j—hj“ubj˜)”}”(hŒunsigned long reqprot”h]”(jQ)”}”(hŒunsigned”h]”hŒunsigned”…””}”(hj h²hh³Nh´Nubah}”(h]”h ]”j]ah"]”h$]”h&]”uh1jPhjubjb)”}”(hŒ ”h]”hŒ ”…””}”(hj.h²hh³Nh´Nubah}”(h]”h ]”jnah"]”h$]”h&]”uh1jahjubjQ)”}”(hŒlong”h]”hŒlong”…””}”(hj<h²hh³Nh´Nubah}”(h]”h ]”j]ah"]”h$]”h&]”uh1jPhjubjb)”}”(hŒ ”h]”hŒ ”…””}”(hjJh²hh³Nh´Nubah}”(h]”h ]”jnah"]”h$]”h&]”uh1jahjubjy)”}”(hŒreqprot”h]”hŒreqprot”…””}”(hjXh²hh³Nh´Nubah}”(h]”h ]”j…ah"]”h$]”h&]”uh1jxhjubeh}”(h]”h ]”h"]”h$]”h&]”Œnoemph”ˆhÅhÆuh1j—hj“ubj˜)”}”(hŒunsigned long prot”h]”(jQ)”}”(hŒunsigned”h]”hŒunsigned”…””}”(hjqh²hh³Nh´Nubah}”(h]”h ]”j]ah"]”h$]”h&]”uh1jPhjmubjb)”}”(hŒ ”h]”hŒ ”…””}”(hjh²hh³Nh´Nubah}”(h]”h ]”jnah"]”h$]”h&]”uh1jahjmubjQ)”}”(hŒlong”h]”hŒlong”…””}”(hjh²hh³Nh´Nubah}”(h]”h ]”j]ah"]”h$]”h&]”uh1jPhjmubjb)”}”(hŒ ”h]”hŒ ”…””}”(hj›h²hh³Nh´Nubah}”(h]”h ]”jnah"]”h$]”h&]”uh1jahjmubjy)”}”(hŒprot”h]”hŒprot”…””}”(hj©h²hh³Nh´Nubah}”(h]”h ]”j…ah"]”h$]”h&]”uh1jxhjmubeh}”(h]”h ]”h"]”h$]”h&]”Œnoemph”ˆhÅhÆuh1j—hj“ubeh}”(h]”h ]”h"]”h$]”h&]”hÅhÆuh1j‘hjLh²hh³hÇh´Kubj÷)”}”(hŒ;”h]”hŒ;”…””}”(hjÄh²hh³Nh´Nubah}”(h]”h ]”jah"]”h$]”h&]”uh1jöhjLh²hh³hÇh´Kubeh}”(h]”h ]”h"]”h$]”h&]”hÅhÆŒ add_permalink”ˆuh1jJŒsphinx_line_type”Œ declarator”hjFh²hh³hÇh´Kubah}”(h]”j=ah ]”(Œsig”Œ sig-object”eh"]”h$]”h&]”Œ is_multiline”ˆŒ _toc_parts”)Œ _toc_name”huh1jDh³hÇh´KhjAh²hubhŒ desc_content”“”)”}”(hhh]”h}”(h]”h ]”h"]”h$]”h&]”uh1jæhjAh²hh³hÇh´Kubeh}”(h]”h ]”(jÔŒfunction”eh"]”h$]”h&]”Œdomain”jÔŒobjtype”jôŒdesctype”jôŒnoindex”‰Œ noindexentry”‰Œnocontentsentry”‰uh1j?h²hhhûh³Nh´Nubhì)”}”(hŒROther LSM hooks which can be instrumented can be found in ``security/security.c``.”h]”(hŒ:Other LSM hooks which can be instrumented can be found in ”…””}”(hjþh²hh³Nh´Nubj)”}”(hŒ``security/security.c``”h]”hŒsecurity/security.c”…””}”(hjh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjþubhŒ.”…””}”(hjþh²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´Khhûh²hubhì)”}”(hX eBPF programs that use Documentation/bpf/btf.rst do not need to include kernel headers for accessing information from the attached eBPF program's context. They can simply declare the structures in the eBPF program and only specify the fields that need to be accessed.”h]”hX eBPF programs that use Documentation/bpf/btf.rst do not need to include kernel headers for accessing information from the attached eBPF program’s context. They can simply declare the structures in the eBPF program and only specify the fields that need to be accessed.”…””}”(hjh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´Khhûh²hubhŒ literal_block”“”)”}”(hX.struct mm_struct { unsigned long start_brk, brk, start_stack; } __attribute__((preserve_access_index)); struct vm_area_struct { unsigned long start_brk, brk, start_stack; unsigned long vm_start, vm_end; struct mm_struct *vm_mm; } __attribute__((preserve_access_index));”h]”hX.struct mm_struct { unsigned long start_brk, brk, start_stack; } __attribute__((preserve_access_index)); struct vm_area_struct { unsigned long start_brk, brk, start_stack; unsigned long vm_start, vm_end; struct mm_struct *vm_mm; } __attribute__((preserve_access_index));”…””}”hj.sbah}”(h]”h ]”h"]”h$]”h&]”hÅhÆŒforce”‰Œlanguage”jÔŒhighlight_args”}”uh1j,h³hÇh´Khhûh²hubhŒnote”“”)”}”(hŒ&The order of the fields is irrelevant.”h]”hì)”}”(hjDh]”hŒ&The order of the fields is irrelevant.”…””}”(hjFh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´K)hjBubah}”(h]”h ]”h"]”h$]”h&]”uh1j@hhûh²hh³hÇh´Nubhì)”}”(hŒ}This can be further simplified (if one has access to the BTF information at build time) by generating the ``vmlinux.h`` with:”h]”(hŒjThis can be further simplified (if one has access to the BTF information at build time) by generating the ”…””}”(hjYh²hh³Nh´Nubj)”}”(hŒ ``vmlinux.h``”h]”hŒ vmlinux.h”…””}”(hjah²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjYubhŒ with:”…””}”(hjYh²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´K+hhûh²hubj-)”}”(hŒB# bpftool btf dump file format c > vmlinux.h”h]”hŒB# bpftool btf dump file format c > vmlinux.h”…””}”hjysbah}”(h]”h ]”h"]”h$]”h&]”hÅhÆj<‰j=Œconsole”j>}”uh1j,h³hÇh´K.hhûh²hubjA)”}”(hŒ``path-to-btf-vmlinux`` can be ``/sys/kernel/btf/vmlinux`` if the build environment matches the environment the BPF programs are deployed in.”h]”hì)”}”(hŒ``path-to-btf-vmlinux`` can be ``/sys/kernel/btf/vmlinux`` if the build environment matches the environment the BPF programs are deployed in.”h]”(j)”}”(hŒ``path-to-btf-vmlinux``”h]”hŒpath-to-btf-vmlinux”…””}”(hj‘h²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjubhŒ can be ”…””}”(hjh²hh³Nh´Nubj)”}”(hŒ``/sys/kernel/btf/vmlinux``”h]”hŒ/sys/kernel/btf/vmlinux”…””}”(hj£h²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjubhŒS if the build environment matches the environment the BPF programs are deployed in.”…””}”(hjh²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´K2hj‰ubah}”(h]”h ]”h"]”h$]”h&]”uh1j@hhûh²hh³hÇh´Nubhì)”}”(hŒpThe ``vmlinux.h`` can then simply be included in the BPF programs without requiring the definition of the types.”h]”(hŒThe ”…””}”(hjÁh²hh³Nh´Nubj)”}”(hŒ ``vmlinux.h``”h]”hŒ vmlinux.h”…””}”(hjÉh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjÁubhŒ_ can then simply be included in the BPF programs without requiring the definition of the types.”…””}”(hjÁh²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´K6hhûh²hubhì)”}”(hŒzThe eBPF programs can be declared using the``BPF_PROG`` macros defined in `tools/lib/bpf/bpf_tracing.h`_. In this example:”h]”(hŒJThe eBPF programs can be declared using the``BPF_PROG`` macros defined in ”…””}”(hjáh²hh³Nh´NubhŒ reference”“”)”}”(hŒ`tools/lib/bpf/bpf_tracing.h`_”h]”hŒtools/lib/bpf/bpf_tracing.h”…””}”(hjëh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”Œname”Œtools/lib/bpf/bpf_tracing.h”Œrefuri”Œahttps://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/tree/tools/lib/bpf/bpf_tracing.h”uh1jéhjáŒresolved”KubhŒ. In this example:”…””}”(hjáh²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´K9hhûh²hubhŒ block_quote”“”)”}”(hŒ* ``"lsm/file_mprotect"`` indicates the LSM hook that the program must be attached to * ``mprotect_audit`` is the name of the eBPF program ”h]”hŒ bullet_list”“”)”}”(hhh]”(hŒ list_item”“”)”}”(hŒS``"lsm/file_mprotect"`` indicates the LSM hook that the program must be attached to”h]”hì)”}”(hŒS``"lsm/file_mprotect"`` indicates the LSM hook that the program must be attached to”h]”(j)”}”(hŒ``"lsm/file_mprotect"``”h]”hŒ"lsm/file_mprotect"”…””}”(hjh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjubhŒ< indicates the LSM hook that the program must be attached to”…””}”(hjh²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´K=hjubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjubj)”}”(hŒ3``mprotect_audit`` is the name of the eBPF program ”h]”hì)”}”(hŒ2``mprotect_audit`` is the name of the eBPF program”h]”(j)”}”(hŒ``mprotect_audit``”h]”hŒmprotect_audit”…””}”(hjCh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhj?ubhŒ is the name of the eBPF program”…””}”(hj?h²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´K?hj;ubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjubeh}”(h]”h ]”h"]”h$]”h&]”Œbullet”júuh1jh³hÇh´K=hj ubah}”(h]”h ]”h"]”h$]”h&]”uh1jh³hÇh´K=hhûh²hubj-)”}”(hXiSEC("lsm/file_mprotect") int BPF_PROG(mprotect_audit, struct vm_area_struct *vma, unsigned long reqprot, unsigned long prot, int ret) { /* ret is the return value from the previous BPF program * or 0 if it's the first hook. */ if (ret != 0) return ret; int is_heap; is_heap = (vma->vm_start >= vma->vm_mm->start_brk && vma->vm_end <= vma->vm_mm->brk); /* Return an -EPERM or write information to the perf events buffer * for auditing */ if (is_heap) return -EPERM; }”h]”hXiSEC("lsm/file_mprotect") int BPF_PROG(mprotect_audit, struct vm_area_struct *vma, unsigned long reqprot, unsigned long prot, int ret) { /* ret is the return value from the previous BPF program * or 0 if it's the first hook. */ if (ret != 0) return ret; int is_heap; is_heap = (vma->vm_start >= vma->vm_mm->start_brk && vma->vm_end <= vma->vm_mm->brk); /* Return an -EPERM or write information to the perf events buffer * for auditing */ if (is_heap) return -EPERM; }”…””}”hjnsbah}”(h]”h ]”h"]”h$]”h&]”hÅhÆj<‰j=jÔj>}”uh1j,h³hÇh´KAhhûh²hubhì)”}”(hX?The ``__attribute__((preserve_access_index))`` is a clang feature that allows the BPF verifier to update the offsets for the access at runtime using the Documentation/bpf/btf.rst information. Since the BPF verifier is aware of the types, it also validates all the accesses made to the various types in the eBPF program.”h]”(hŒThe ”…””}”(hj}h²hh³Nh´Nubj)”}”(hŒ*``__attribute__((preserve_access_index))``”h]”hŒ&__attribute__((preserve_access_index))”…””}”(hj…h²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhj}ubhX is a clang feature that allows the BPF verifier to update the offsets for the access at runtime using the Documentation/bpf/btf.rst information. Since the BPF verifier is aware of the types, it also validates all the accesses made to the various types in the eBPF program.”…””}”(hj}h²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´KYhhûh²hubeh}”(h]”Œ structure”ah ]”h"]”Œ structure”ah$]”h&]”uh1hÖhhØh²hh³hÇh´K ubh×)”}”(hhh]”(hÜ)”}”(hŒLoading”h]”hŒLoading”…””}”(hj¨h²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1hÛhj¥h²hh³hÇh´K`ubhì)”}”(hŒ]eBPF programs can be loaded with the :manpage:`bpf(2)` syscall's ``BPF_PROG_LOAD`` operation:”h]”(hŒ%eBPF programs can be loaded with the ”…””}”(hj¶h²hh³Nh´NubhŒmanpage”“”)”}”(hŒ:manpage:`bpf(2)`”h]”hŒbpf(2)”…””}”(hjÀh²hh³Nh´Nubah}”(h]”h ]”j¾ah"]”h$]”h&]”hÅhÆŒpath”Œbpf(2)”Œpage”Œbpf”Œsection”Œ2”uh1j¾hj¶ubhŒ syscall’s ”…””}”(hj¶h²hh³Nh´Nubj)”}”(hŒ``BPF_PROG_LOAD``”h]”hŒ BPF_PROG_LOAD”…””}”(hjØh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhj¶ubhŒ operation:”…””}”(hj¶h²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´Kbhj¥h²hubj-)”}”(hŒVstruct bpf_object *obj; obj = bpf_object__open("./my_prog.o"); bpf_object__load(obj);”h]”hŒVstruct bpf_object *obj; obj = bpf_object__open("./my_prog.o"); bpf_object__load(obj);”…””}”hjðsbah}”(h]”h ]”h"]”h$]”h&]”hÅhÆj<‰j=jÔj>}”uh1j,h³hÇh´Kehj¥h²hubhì)”}”(hŒKThis can be simplified by using a skeleton header generated by ``bpftool``:”h]”(hŒ?This can be simplified by using a skeleton header generated by ”…””}”(hjÿh²hh³Nh´Nubj)”}”(hŒ ``bpftool``”h]”hŒbpftool”…””}”(hjh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjÿubhŒ:”…””}”(hjÿh²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´Klhj¥h²hubj-)”}”(hŒ1# bpftool gen skeleton my_prog.o > my_prog.skel.h”h]”hŒ1# bpftool gen skeleton my_prog.o > my_prog.skel.h”…””}”hjsbah}”(h]”h ]”h"]”h$]”h&]”hÅhÆj<‰j=Œconsole”j>}”uh1j,h³hÇh´Knhj¥h²hubhì)”}”(hŒyand the program can be loaded by including ``my_prog.skel.h`` and using the generated helper, ``my_prog__open_and_load``.”h]”(hŒ+and the program can be loaded by including ”…””}”(hj/h²hh³Nh´Nubj)”}”(hŒ``my_prog.skel.h``”h]”hŒmy_prog.skel.h”…””}”(hj7h²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhj/ubhŒ! and using the generated helper, ”…””}”(hj/h²hh³Nh´Nubj)”}”(hŒ``my_prog__open_and_load``”h]”hŒmy_prog__open_and_load”…””}”(hjIh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhj/ubhŒ.”…””}”(hj/h²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´Krhj¥h²hubeh}”(h]”Œloading”ah ]”h"]”Œloading”ah$]”h&]”uh1hÖhhØh²hh³hÇh´K`ubh×)”}”(hhh]”(hÜ)”}”(hŒAttachment to LSM Hooks”h]”hŒAttachment to LSM Hooks”…””}”(hjlh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1hÛhjih²hh³hÇh´Kvubhì)”}”(hŒÆThe LSM allows attachment of eBPF programs as LSM hooks using :manpage:`bpf(2)` syscall's ``BPF_RAW_TRACEPOINT_OPEN`` operation or more simply by using the libbpf helper ``bpf_program__attach_lsm``.”h]”(hŒ>The LSM allows attachment of eBPF programs as LSM hooks using ”…””}”(hjzh²hh³Nh´Nubj¿)”}”(hŒ:manpage:`bpf(2)`”h]”hŒbpf(2)”…””}”(hj‚h²hh³Nh´Nubah}”(h]”h ]”j¾ah"]”h$]”h&]”hÅhÆjÎŒbpf(2)”jÐŒbpf”jÒjÓuh1j¾hjzubhŒ syscall’s ”…””}”(hjzh²hh³Nh´Nubj)”}”(hŒ``BPF_RAW_TRACEPOINT_OPEN``”h]”hŒBPF_RAW_TRACEPOINT_OPEN”…””}”(hj–h²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjzubhŒ5 operation or more simply by using the libbpf helper ”…””}”(hjzh²hh³Nh´Nubj)”}”(hŒ``bpf_program__attach_lsm``”h]”hŒbpf_program__attach_lsm”…””}”(hj¨h²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjzubhŒ.”…””}”(hjzh²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´Kxhjih²hubhì)”}”(hŒ”The program can be detached from the LSM hook by *destroying* the ``link`` link returned by ``bpf_program__attach_lsm`` using ``bpf_link__destroy``.”h]”(hŒ1The program can be detached from the LSM hook by ”…””}”(hjÀh²hh³Nh´NubhŒemphasis”“”)”}”(hŒ *destroying*”h]”hŒ destroying”…””}”(hjÊh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jÈhjÀubhŒ the ”…””}”(hjÀh²hh³Nh´Nubj)”}”(hŒ``link``”h]”hŒlink”…””}”(hjÜh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjÀubhŒ link returned by ”…””}”(hjÀh²hh³Nh´Nubj)”}”(hŒ``bpf_program__attach_lsm``”h]”hŒbpf_program__attach_lsm”…””}”(hjîh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjÀubhŒ using ”…””}”(hjÀh²hh³Nh´Nubj)”}”(hŒ``bpf_link__destroy``”h]”hŒbpf_link__destroy”…””}”(hjh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjÀubhŒ.”…””}”(hjÀh²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´K|hjih²hubhì)”}”(hŒŽOne can also use the helpers generated in ``my_prog.skel.h`` i.e. ``my_prog__attach`` for attachment and ``my_prog__destroy`` for cleaning up.”h]”(hŒ*One can also use the helpers generated in ”…””}”(hjh²hh³Nh´Nubj)”}”(hŒ``my_prog.skel.h``”h]”hŒmy_prog.skel.h”…””}”(hj h²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjubhŒ i.e. ”…””}”(hjh²hh³Nh´Nubj)”}”(hŒ``my_prog__attach``”h]”hŒmy_prog__attach”…””}”(hj2h²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjubhŒ for attachment and ”…””}”(hjh²hh³Nh´Nubj)”}”(hŒ``my_prog__destroy``”h]”hŒmy_prog__destroy”…””}”(hjDh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1jhjubhŒ for cleaning up.”…””}”(hjh²hh³Nh´Nubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´Khjih²hubeh}”(h]”Œattachment-to-lsm-hooks”ah ]”h"]”Œattachment to lsm hooks”ah$]”h&]”uh1hÖhhØh²hh³hÇh´Kvubh×)”}”(hhh]”(hÜ)”}”(hŒExamples”h]”hŒExamples”…””}”(hjgh²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”uh1hÛhjdh²hh³hÇh´Kƒubhì)”}”(hŒ¯An example eBPF program can be found in `tools/testing/selftests/bpf/progs/lsm.c`_ and the corresponding userspace code in `tools/testing/selftests/bpf/prog_tests/test_lsm.c`_”h]”(hŒ(An example eBPF program can be found in ”…””}”(hjuh²hh³Nh´Nubjê)”}”(hŒ*`tools/testing/selftests/bpf/progs/lsm.c`_”h]”hŒ'tools/testing/selftests/bpf/progs/lsm.c”…””}”(hj}h²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”Œname”Œ'tools/testing/selftests/bpf/progs/lsm.c”jûŒmhttps://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/tree/tools/testing/selftests/bpf/progs/lsm.c”uh1jéhjujýKubhŒ) and the corresponding userspace code in ”…””}”(hjuh²hh³Nh´Nubjê)”}”(hŒ4`tools/testing/selftests/bpf/prog_tests/test_lsm.c`_”h]”hŒ1tools/testing/selftests/bpf/prog_tests/test_lsm.c”…””}”(hj’h²hh³Nh´Nubah}”(h]”h ]”h"]”h$]”h&]”Œname”Œ1tools/testing/selftests/bpf/prog_tests/test_lsm.c”jûŒwhttps://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/tree/tools/testing/selftests/bpf/prog_tests/test_lsm.c”uh1jéhjujýKubeh}”(h]”h ]”h"]”h$]”h&]”uh1hëh³hÇh´K…hjdh²hubh¶)”}”(hŒLinks”h]”hŒLinks”…””}”hj©sbah}”(h]”h ]”h"]”h$]”h&]”hÅhÆuh1hµhjdh²hh³hÇh´K‰ubhŒtarget”“”)”}”(hŒ….. _tools/lib/bpf/bpf_tracing.h: https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/tree/tools/lib/bpf/bpf_tracing.h”h]”h}”(h]”Œtools-lib-bpf-bpf-tracing-h”ah ]”h"]”Œtools/lib/bpf/bpf_tracing.h”ah$]”h&]”jûjüuh1j·h´KŠhjdh²hh³hÇŒ referenced”Kubj¸)”}”(hŒ.. _tools/testing/selftests/bpf/progs/lsm.c: https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/tree/tools/testing/selftests/bpf/progs/lsm.c”h]”h}”(h]”Œ'tools-testing-selftests-bpf-progs-lsm-c”ah ]”h"]”Œ'tools/testing/selftests/bpf/progs/lsm.c”ah$]”h&]”jûjuh1j·h´KŒhjdh²hh³hÇjÅKubj¸)”}”(hŒ±.. _tools/testing/selftests/bpf/prog_tests/test_lsm.c: https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/tree/tools/testing/selftests/bpf/prog_tests/test_lsm.c”h]”h}”(h]”Œ1tools-testing-selftests-bpf-prog-tests-test-lsm-c”ah ]”h"]”Œ1tools/testing/selftests/bpf/prog_tests/test_lsm.c”ah$]”h&]”jûj¢uh1j·h´KŽhjdh²hh³hÇjÅKubeh}”(h]”Œexamples”ah ]”h"]”Œexamples”ah$]”h&]”uh1hÖhhØh²hh³hÇh´Kƒubeh}”(h]”Œlsm-bpf-programs”ah ]”h"]”Œlsm bpf programs”ah$]”h&]”uh1hÖhhh²hh³hÇh´Kubeh}”(h]”h ]”h"]”h$]”h&]”Œsource”hÇuh1hŒcurrent_source”NŒ current_line”NŒsettings”Œdocutils.frontend”ŒValues”“”)”}”(hÛNŒ generator”NŒ datestamp”NŒ source_link”NŒ source_url”NŒ toc_backlinks”Œentry”Œfootnote_backlinks”KŒ sectnum_xform”KŒstrip_comments”NŒstrip_elements_with_classes”NŒ strip_classes”NŒ report_level”KŒ halt_level”KŒexit_status_level”KŒdebug”NŒwarning_stream”NŒ traceback”ˆŒinput_encoding”Œ utf-8-sig”Œinput_encoding_error_handler”Œstrict”Œoutput_encoding”Œutf-8”Œoutput_encoding_error_handler”jŒerror_encoding”Œutf-8”Œerror_encoding_error_handler”Œbackslashreplace”Œ language_code”Œen”Œrecord_dependencies”NŒconfig”NŒ id_prefix”hŒauto_id_prefix”Œid”Œ dump_settings”NŒdump_internals”NŒdump_transforms”NŒdump_pseudo_xml”NŒexpose_internals”NŒstrict_visitor”NŒ_disable_config”NŒ_source”hÇŒ _destination”NŒ _config_files”]”Œ7/var/lib/git/docbuild/linux/Documentation/docutils.conf”aŒfile_insertion_enabled”ˆŒ raw_enabled”KŒline_length_limit”M'Œpep_references”NŒ pep_base_url”Œhttps://peps.python.org/”Œpep_file_url_template”Œpep-%04d”Œrfc_references”NŒ rfc_base_url”Œ&https://datatracker.ietf.org/doc/html/”Œ tab_width”KŒtrim_footnote_reference_space”‰Œsyntax_highlight”Œlong”Œ smart_quotes”ˆŒsmartquotes_locales”]”Œcharacter_level_inline_markup”‰Œdoctitle_xform”‰Œ docinfo_xform”KŒsectsubtitle_xform”‰Œ image_loading”Œlink”Œembed_stylesheet”‰Œcloak_email_addresses”ˆŒsection_self_link”‰Œenv”NubŒreporter”NŒindirect_targets”]”Œsubstitution_defs”}”Œsubstitution_names”}”Œrefnames”}”(Œtools/lib/bpf/bpf_tracing.h”]”jëaŒ'tools/testing/selftests/bpf/progs/lsm.c”]”j}aŒ1tools/testing/selftests/bpf/prog_tests/test_lsm.c”]”j’auŒrefids”}”Œnameids”}”(jëjèj¢jŸjfjcjaj^jãjàjÂj¿jÏjÌjÛjØuŒ nametypes”}”(jë‰j¢‰jf‰ja‰jã‰jˆjψjÛˆuh}”(jèhØjŸhûj=jFjcj¥j^jijàjdj¿j¹jÌjÆjØjÒuŒ footnote_refs”}”Œ citation_refs”}”Œ autofootnotes”]”Œautofootnote_refs”]”Œsymbol_footnotes”]”Œsymbol_footnote_refs”]”Œ footnotes”]”Œ citations”]”Œautofootnote_start”KŒsymbol_footnote_start”KŒ id_counter”Œ collections”ŒCounter”“”}”…”R”Œparse_messages”]”Œtransform_messages”]”Œ transformer”NŒ include_log”]”Œ decoration”Nh²hub.