xref: /aosp_15_r20/external/compiler-rt/test/scudo/sizes.cpp (revision 7c3d14c8b49c529e04be81a3ce6f5cc23712e4c6)
1*7c3d14c8STreehugger Robot // RUN: %clang_scudo %s -o %t
2*7c3d14c8STreehugger Robot // RUN: SCUDO_OPTIONS=allocator_may_return_null=0 not %run %t malloc 2>&1 | FileCheck %s
3*7c3d14c8STreehugger Robot // RUN: SCUDO_OPTIONS=allocator_may_return_null=1     %run %t malloc 2>&1
4*7c3d14c8STreehugger Robot // RUN: SCUDO_OPTIONS=allocator_may_return_null=0 not %run %t calloc 2>&1 | FileCheck %s
5*7c3d14c8STreehugger Robot // RUN: SCUDO_OPTIONS=allocator_may_return_null=1     %run %t calloc 2>&1
6*7c3d14c8STreehugger Robot // RUN:                                               %run %t usable 2>&1
7*7c3d14c8STreehugger Robot 
8*7c3d14c8STreehugger Robot // Tests for various edge cases related to sizes, notably the maximum size the
9*7c3d14c8STreehugger Robot // allocator can allocate. Tests that an integer overflow in the parameters of
10*7c3d14c8STreehugger Robot // calloc is caught.
11*7c3d14c8STreehugger Robot 
12*7c3d14c8STreehugger Robot #include <assert.h>
13*7c3d14c8STreehugger Robot #include <malloc.h>
14*7c3d14c8STreehugger Robot #include <stdlib.h>
15*7c3d14c8STreehugger Robot #include <string.h>
16*7c3d14c8STreehugger Robot 
17*7c3d14c8STreehugger Robot #include <limits>
18*7c3d14c8STreehugger Robot 
main(int argc,char ** argv)19*7c3d14c8STreehugger Robot int main(int argc, char **argv)
20*7c3d14c8STreehugger Robot {
21*7c3d14c8STreehugger Robot   assert(argc == 2);
22*7c3d14c8STreehugger Robot   if (!strcmp(argv[1], "malloc")) {
23*7c3d14c8STreehugger Robot     // Currently the maximum size the allocator can allocate is 1ULL<<40 bytes.
24*7c3d14c8STreehugger Robot     size_t size = std::numeric_limits<size_t>::max();
25*7c3d14c8STreehugger Robot     void *p = malloc(size);
26*7c3d14c8STreehugger Robot     if (p)
27*7c3d14c8STreehugger Robot       return 1;
28*7c3d14c8STreehugger Robot     size = (1ULL << 40) - 16;
29*7c3d14c8STreehugger Robot     p = malloc(size);
30*7c3d14c8STreehugger Robot     if (p)
31*7c3d14c8STreehugger Robot       return 1;
32*7c3d14c8STreehugger Robot   }
33*7c3d14c8STreehugger Robot   if (!strcmp(argv[1], "calloc")) {
34*7c3d14c8STreehugger Robot     // Trigger an overflow in calloc.
35*7c3d14c8STreehugger Robot     size_t size = std::numeric_limits<size_t>::max();
36*7c3d14c8STreehugger Robot     void *p = calloc((size / 0x1000) + 1, 0x1000);
37*7c3d14c8STreehugger Robot     if (p)
38*7c3d14c8STreehugger Robot       return 1;
39*7c3d14c8STreehugger Robot   }
40*7c3d14c8STreehugger Robot   if (!strcmp(argv[1], "usable")) {
41*7c3d14c8STreehugger Robot     // Playing with the actual usable size of a chunk.
42*7c3d14c8STreehugger Robot     void *p = malloc(1007);
43*7c3d14c8STreehugger Robot     if (!p)
44*7c3d14c8STreehugger Robot       return 1;
45*7c3d14c8STreehugger Robot     size_t size = malloc_usable_size(p);
46*7c3d14c8STreehugger Robot     if (size < 1007)
47*7c3d14c8STreehugger Robot       return 1;
48*7c3d14c8STreehugger Robot     memset(p, 'A', size);
49*7c3d14c8STreehugger Robot     p = realloc(p, 2014);
50*7c3d14c8STreehugger Robot     if (!p)
51*7c3d14c8STreehugger Robot       return 1;
52*7c3d14c8STreehugger Robot     size = malloc_usable_size(p);
53*7c3d14c8STreehugger Robot     if (size < 2014)
54*7c3d14c8STreehugger Robot       return 1;
55*7c3d14c8STreehugger Robot     memset(p, 'B', size);
56*7c3d14c8STreehugger Robot     free(p);
57*7c3d14c8STreehugger Robot   }
58*7c3d14c8STreehugger Robot   return 0;
59*7c3d14c8STreehugger Robot }
60*7c3d14c8STreehugger Robot 
61*7c3d14c8STreehugger Robot // CHECK: allocator is terminating the process
62