| // RUN: %clang_esan_wset -O0 %s -o %t 2>&1 |
| // RUN: %env_esan_opts="verbosity=1 record_snapshots=0" %run %t %t 2>&1 | FileCheck %s |
| |
| #include <assert.h> |
| #include <stdio.h> |
| #include <sys/mman.h> |
| #include <sys/resource.h> |
| #include <sys/types.h> |
| #include <sys/wait.h> |
| #include <unistd.h> |
| |
| static void testChildStackLimit(rlim_t StackLimit, char *ToRun) { |
| int Res; |
| struct rlimit Limit; |
| Limit.rlim_cur = RLIM_INFINITY; |
| Limit.rlim_max = RLIM_INFINITY; |
| Res = setrlimit(RLIMIT_STACK, &Limit); |
| if (Res != 0) { |
| // Probably our environment had a large limit and we ourselves got |
| // re-execed and can no longer raise our limit. |
| // We have to bail and emulate the regular test. |
| // We'd prefer to have branches in our FileCheck output to ensure the |
| // initial program was re-execed but this is the best we can do for now. |
| fprintf(stderr, "in esan::initializeLibrary\n"); |
| fprintf(stderr, "==1234==The stack size limit is beyond the maximum supported.\n"); |
| fprintf(stderr, "Re-execing with a stack size below 1TB.\n"); |
| fprintf(stderr, "in esan::initializeLibrary\n"); |
| fprintf(stderr, "done\n"); |
| fprintf(stderr, "in esan::finalizeLibrary\n"); |
| return; |
| } |
| |
| pid_t Child = fork(); |
| assert(Child >= 0); |
| if (Child > 0) { |
| pid_t WaitRes = waitpid(Child, NULL, 0); |
| assert(WaitRes == Child); |
| } else { |
| char *Args[2]; |
| Args[0] = ToRun; |
| Args[1] = NULL; |
| Res = execv(ToRun, Args); |
| assert(0); // Should not be reached. |
| } |
| } |
| |
| int main(int argc, char *argv[]) { |
| // The path to the program to exec must be passed in the first time. |
| if (argc == 2) { |
| fprintf(stderr, "Testing child with infinite stack\n"); |
| testChildStackLimit(RLIM_INFINITY, argv[1]); |
| fprintf(stderr, "Testing child with 1TB stack\n"); |
| testChildStackLimit(1ULL << 40, argv[1]); |
| } |
| fprintf(stderr, "done\n"); |
| // CHECK: in esan::initializeLibrary |
| // CHECK: Testing child with infinite stack |
| // CHECK-NEXT: in esan::initializeLibrary |
| // CHECK-NEXT: =={{[0-9:]+}}==The stack size limit is beyond the maximum supported. |
| // CHECK-NEXT: Re-execing with a stack size below 1TB. |
| // CHECK-NEXT: in esan::initializeLibrary |
| // CHECK: done |
| // CHECK: in esan::finalizeLibrary |
| // CHECK: Testing child with 1TB stack |
| // CHECK-NEXT: in esan::initializeLibrary |
| // CHECK-NEXT: =={{[0-9:]+}}==The stack size limit is beyond the maximum supported. |
| // CHECK-NEXT: Re-execing with a stack size below 1TB. |
| // CHECK-NEXT: in esan::initializeLibrary |
| // CHECK: done |
| // CHECK-NEXT: in esan::finalizeLibrary |
| // CHECK: done |
| // CHECK-NEXT: in esan::finalizeLibrary |
| return 0; |
| } |