Merge tag 'hardening-v6.2-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/kees...
[platform/kernel/linux-rpi.git] / mm / slab_common.c
index 7e96abf..1cba98a 100644 (file)
@@ -143,8 +143,10 @@ int slab_unmergeable(struct kmem_cache *s)
        if (s->ctor)
                return 1;
 
+#ifdef CONFIG_HARDENED_USERCOPY
        if (s->usersize)
                return 1;
+#endif
 
        /*
         * We may have set a slab to be unmergeable during bootstrap.
@@ -223,8 +225,10 @@ static struct kmem_cache *create_cache(const char *name,
        s->size = s->object_size = object_size;
        s->align = align;
        s->ctor = ctor;
+#ifdef CONFIG_HARDENED_USERCOPY
        s->useroffset = useroffset;
        s->usersize = usersize;
+#endif
 
        err = __kmem_cache_create(s, flags);
        if (err)
@@ -317,7 +321,8 @@ kmem_cache_create_usercopy(const char *name,
        flags &= CACHE_CREATE_MASK;
 
        /* Fail closed on bad usersize of useroffset values. */
-       if (WARN_ON(!usersize && useroffset) ||
+       if (!IS_ENABLED(CONFIG_HARDENED_USERCOPY) ||
+           WARN_ON(!usersize && useroffset) ||
            WARN_ON(size < usersize || size - usersize < useroffset))
                usersize = useroffset = 0;
 
@@ -595,8 +600,8 @@ void kmem_dump_obj(void *object)
                ptroffset = ((char *)object - (char *)kp.kp_objp) - kp.kp_data_offset;
                pr_cont(" pointer offset %lu", ptroffset);
        }
-       if (kp.kp_slab_cache && kp.kp_slab_cache->usersize)
-               pr_cont(" size %u", kp.kp_slab_cache->usersize);
+       if (kp.kp_slab_cache && kp.kp_slab_cache->object_size)
+               pr_cont(" size %u", kp.kp_slab_cache->object_size);
        if (kp.kp_ret)
                pr_cont(" allocated at %pS\n", kp.kp_ret);
        else
@@ -640,8 +645,10 @@ void __init create_boot_cache(struct kmem_cache *s, const char *name,
                align = max(align, size);
        s->align = calculate_alignment(flags, align, size);
 
+#ifdef CONFIG_HARDENED_USERCOPY
        s->useroffset = useroffset;
        s->usersize = usersize;
+#endif
 
        err = __kmem_cache_create(s, flags);
 
@@ -766,10 +773,16 @@ EXPORT_SYMBOL(kmalloc_size_roundup);
 #define KMALLOC_CGROUP_NAME(sz)
 #endif
 
+#ifndef CONFIG_SLUB_TINY
+#define KMALLOC_RCL_NAME(sz)   .name[KMALLOC_RECLAIM] = "kmalloc-rcl-" #sz,
+#else
+#define KMALLOC_RCL_NAME(sz)
+#endif
+
 #define INIT_KMALLOC_INFO(__size, __short_size)                        \
 {                                                              \
        .name[KMALLOC_NORMAL]  = "kmalloc-" #__short_size,      \
-       .name[KMALLOC_RECLAIM] = "kmalloc-rcl-" #__short_size,  \
+       KMALLOC_RCL_NAME(__short_size)                          \
        KMALLOC_CGROUP_NAME(__short_size)                       \
        KMALLOC_DMA_NAME(__short_size)                          \
        .size = __size,                                         \
@@ -855,7 +868,7 @@ void __init setup_kmalloc_cache_index_table(void)
 static void __init
 new_kmalloc_cache(int idx, enum kmalloc_cache_type type, slab_flags_t flags)
 {
-       if (type == KMALLOC_RECLAIM) {
+       if ((KMALLOC_RECLAIM != KMALLOC_NORMAL) && (type == KMALLOC_RECLAIM)) {
                flags |= SLAB_RECLAIM_ACCOUNT;
        } else if (IS_ENABLED(CONFIG_MEMCG_KMEM) && (type == KMALLOC_CGROUP)) {
                if (mem_cgroup_kmem_disabled()) {
@@ -941,7 +954,7 @@ void *__do_kmalloc_node(size_t size, gfp_t flags, int node, unsigned long caller
 
        if (unlikely(size > KMALLOC_MAX_CACHE_SIZE)) {
                ret = __kmalloc_large_node(size, flags, node);
-               trace_kmalloc(_RET_IP_, ret, size,
+               trace_kmalloc(caller, ret, size,
                              PAGE_SIZE << get_order(size), flags, node);
                return ret;
        }
@@ -953,7 +966,7 @@ void *__do_kmalloc_node(size_t size, gfp_t flags, int node, unsigned long caller
 
        ret = __kmem_cache_alloc_node(s, flags, node, size, caller);
        ret = kasan_kmalloc(s, ret, size, flags);
-       trace_kmalloc(_RET_IP_, ret, size, s->size, flags, node);
+       trace_kmalloc(caller, ret, size, s->size, flags, node);
        return ret;
 }
 
@@ -1010,7 +1023,7 @@ EXPORT_SYMBOL(kfree);
 
 /**
  * __ksize -- Report full size of underlying allocation
- * @objp: pointer to the object
+ * @object: pointer to the object
  *
  * This should only be used internally to query the true size of allocations.
  * It is not meant to be a way to discover the usable size of an allocation
@@ -1018,7 +1031,7 @@ EXPORT_SYMBOL(kfree);
  * the originally requested allocation size may trigger KASAN, UBSAN_BOUNDS,
  * and/or FORTIFY_SOURCE.
  *
- * Return: size of the actual memory used by @objp in bytes
+ * Return: size of the actual memory used by @object in bytes
  */
 size_t __ksize(const void *object)
 {
@@ -1037,10 +1050,13 @@ size_t __ksize(const void *object)
                return folio_size(folio);
        }
 
+#ifdef CONFIG_SLUB_DEBUG
+       skip_orig_size_check(folio_slab(folio)->slab_cache, object);
+#endif
+
        return slab_ksize(folio_slab(folio)->slab_cache);
 }
 
-#ifdef CONFIG_TRACING
 void *kmalloc_trace(struct kmem_cache *s, gfp_t gfpflags, size_t size)
 {
        void *ret = __kmem_cache_alloc_node(s, gfpflags, NUMA_NO_NODE,
@@ -1064,7 +1080,6 @@ void *kmalloc_node_trace(struct kmem_cache *s, gfp_t gfpflags,
        return ret;
 }
 EXPORT_SYMBOL(kmalloc_node_trace);
-#endif /* !CONFIG_TRACING */
 #endif /* !CONFIG_SLOB */
 
 gfp_t kmalloc_fix_flags(gfp_t flags)
@@ -1413,20 +1428,6 @@ void kfree_sensitive(const void *p)
 }
 EXPORT_SYMBOL(kfree_sensitive);
 
-/**
- * ksize - get the actual amount of memory allocated for a given object
- * @objp: Pointer to the object
- *
- * kmalloc may internally round up allocations and return more memory
- * than requested. ksize() can be used to determine the actual amount of
- * memory allocated. The caller may use this additional memory, even though
- * a smaller amount of memory was initially specified with the kmalloc call.
- * The caller must guarantee that objp points to a valid object previously
- * allocated with either kmalloc() or kmem_cache_alloc(). The object
- * must not be freed during the duration of the call.
- *
- * Return: size of the actual memory used by @objp in bytes
- */
 size_t ksize(const void *objp)
 {
        /*