• A
    kasan: check KASAN_NO_FREE_META in __kasan_metadata_size · d5c5dc51
    Andrey Konovalov 提交于
    mainline inclusion
    from mainline-v6.1-rc1
    commit ca77f290
    category: bugfix
    bugzilla: 187796, https://gitee.com/openeuler/kernel/issues/I5W6YV
    CVE: NA
    
    Reference: https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=ca77f290cff1dfa095d71ae16cc7cda8ee6df495
    
    --------------------------------
    
    Patch series "kasan: switch tag-based modes to stack ring from per-object
    metadata", v3.
    
    This series makes the tag-based KASAN modes use a ring buffer for storing
    stack depot handles for alloc/free stack traces for slab objects instead
    of per-object metadata.  This ring buffer is referred to as the stack
    ring.
    
    On each alloc/free of a slab object, the tagged address of the object and
    the current stack trace are recorded in the stack ring.
    
    On each bug report, if the accessed address belongs to a slab object, the
    stack ring is scanned for matching entries.  The newest entries are used
    to print the alloc/free stack traces in the report: one entry for alloc
    and one for free.
    
    The advantages of this approach over storing stack trace handles in
    per-object metadata with the tag-based KASAN modes:
    
    - Allows to find relevant stack traces for use-after-free bugs without
      using quarantine for freed memory. (Currently, if the object was
      reallocated multiple times, the report contains the latest alloc/free
      stack traces, not necessarily the ones relevant to the buggy allocation.)
    - Allows to better identify and mark use-after-free bugs, effectively
      making the CONFIG_KASAN_TAGS_IDENTIFY functionality always-on.
    - Has fixed memory overhead.
    
    The disadvantage:
    
    - If the affected object was allocated/freed long before the bug happened
      and the stack trace events were purged from the stack ring, the report
      will have no stack traces.
    
    Discussion
    
    ==========
    
    The proposed implementation of the stack ring uses a single ring buffer
    for the whole kernel.  This might lead to contention due to atomic
    accesses to the ring buffer index on multicore systems.
    
    At this point, it is unknown whether the performance impact from this
    contention would be significant compared to the slowdown introduced by
    collecting stack traces due to the planned changes to the latter part, see
    the section below.
    
    For now, the proposed implementation is deemed to be good enough, but this
    might need to be revisited once the stack collection becomes faster.
    
    A considered alternative is to keep a separate ring buffer for each CPU
    and then iterate over all of them when printing a bug report.  This
    approach requires somehow figuring out which of the stack rings has the
    freshest stack traces for an object if multiple stack rings have them.
    
    Further plans
    =============
    
    This series is a part of an effort to make KASAN stack trace collection
    suitable for production.  This requires stack trace collection to be fast
    and memory-bounded.
    
    The planned steps are:
    
    1. Speed up stack trace collection (potentially, by using SCS;
       patches on-hold until steps #2 and #3 are completed).
    2. Keep stack trace handles in the stack ring (this series).
    3. Add a memory-bounded mode to stack depot or provide an alternative
       memory-bounded stack storage.
    4. Potentially, implement stack trace collection sampling to minimize
       the performance impact.
    
    This patch (of 34):
    
    __kasan_metadata_size() calculates the size of the redzone for objects in
    a slab cache.
    
    When accounting for presence of kasan_free_meta in the redzone, this
    function only compares free_meta_offset with 0.  But free_meta_offset
    could also be equal to KASAN_NO_FREE_META, which indicates that
    kasan_free_meta is not present at all.
    
    Add a comparison with KASAN_NO_FREE_META into __kasan_metadata_size().
    
    Link: https://lkml.kernel.org/r/cover.1662411799.git.andreyknvl@google.com
    Link: https://lkml.kernel.org/r/c7b316d30d90e5947eb8280f4dc78856a49298cf.1662411799.git.andreyknvl@google.comSigned-off-by: NAndrey Konovalov <andreyknvl@google.com>
    Reviewed-by: NMarco Elver <elver@google.com>
    Cc: Alexander Potapenko <glider@google.com>
    Cc: Andrey Ryabinin <ryabinin.a.a@gmail.com>
    Cc: Dmitry Vyukov <dvyukov@google.com>
    Cc: Evgenii Stepanov <eugenis@google.com>
    Cc: Peter Collingbourne <pcc@google.com>
    Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
    Signed-off-by: NLiu Shixin <liushixin2@huawei.com>
    Reviewed-by: NKefeng Wang <wangkefeng.wang@huawei.com>
    Signed-off-by: NZheng Zengkai <zhengzengkai@huawei.com>
    d5c5dc51
common.c 28.1 KB