File: gcov-dlopen.c

package info (click to toggle)
swiftlang 6.0.3-2
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 2,519,992 kB
  • sloc: cpp: 9,107,863; ansic: 2,040,022; asm: 1,135,751; python: 296,500; objc: 82,456; f90: 60,502; lisp: 34,951; pascal: 19,946; sh: 18,133; perl: 7,482; ml: 4,937; javascript: 4,117; makefile: 3,840; awk: 3,535; xml: 914; fortran: 619; cs: 573; ruby: 573
file content (87 lines) | stat: -rw-r--r-- 3,591 bytes parent folder | download | duplicates (6)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
/// atexit(3) not supported in dlopen(3)ed+dlclose(3)d DSO
// XFAIL: target={{.*netbsd.*}}

// RUN: mkdir -p %t.d && cd %t.d

// RUN: echo 'void func1(int k) {}' > func1.c
// RUN: echo 'void func2(int k) {}' > func2.c
// RUN: echo 'void func3(int k) {}' > func3.c
// RUN: %clang --coverage -fPIC -shared func1.c -o func1.so -dumpdir ./
// RUN: %clang --coverage -fPIC -shared func2.c -o func2.so -dumpdir ./
// RUN: %clang --coverage -fPIC -shared func3.c -o func3.so -dumpdir ./
// RUN: %clang --coverage -fPIC -rpath %t.d %s -o %t -dumpdir ./

/// Test with two dlopened libraries.
// RUN: rm -f gcov-dlopen.gcda func1.gcda func2.gcda
// RUN: %run %t
// RUN: llvm-cov gcov -t gcov-dlopen.gcda | FileCheck %s
// RUN: llvm-cov gcov -t func1.gcda | FileCheck %s --check-prefix=FUNC1
// RUN: llvm-cov gcov -t func2.gcda | FileCheck %s --check-prefix=FUNC2

// FUNC1:     1:    1:void func1(int k) {}
// FUNC2:     1:    1:void func2(int k) {}

/// Test with three dlopened libraries.
// RUN: %clang -DUSE_LIB3 --coverage -fPIC -rpath %t.d %s -o %t -dumpdir ./
// RUN: rm -f gcov-dlopen.gcda func1.gcda func2.gcda func3.gcda
// RUN: %run %t
// RUN: llvm-cov gcov -t gcov-dlopen.gcda | FileCheck %s --check-prefix=LIB3
// RUN: llvm-cov gcov -t func1.gcda | FileCheck %s --check-prefix=FUNC1
// RUN: llvm-cov gcov -t func2.gcda | FileCheck %s --check-prefix=FUNC2
// RUN: llvm-cov gcov -t func3.gcda | FileCheck %s --check-prefix=FUNC3

// FUNC3:     1:    1:void func3(int k) {}

#include <dlfcn.h>
#include <stdio.h>
#include <stdlib.h>

int main(int argc, char *argv[]) {
  void *f1_handle = dlopen("func1.so", RTLD_LAZY | RTLD_GLOBAL);
  if (f1_handle == NULL)
    return fprintf(stderr, "unable to open 'func1.so': %s\n", dlerror());
  void (*func1)(void) = (void (*)(void))dlsym(f1_handle, "func1");
  if (func1 == NULL)
    return fprintf(stderr, "unable to lookup symbol 'func1': %s\n", dlerror());

  void *f2_handle = dlopen("func2.so", RTLD_LAZY | RTLD_GLOBAL);
  if (f2_handle == NULL)
    return fprintf(stderr, "unable to open 'func2.so': %s\n", dlerror());
  void (*func2)(void) = (void (*)(void))dlsym(f2_handle, "func2");
  if (func2 == NULL)
    return fprintf(stderr, "unable to lookup symbol 'func2': %s\n", dlerror());
  func2();

#ifdef USE_LIB3
// CHECK:          -: [[#@LINE+2]]:  void *f3_handle
// LIB3:           1: [[#@LINE+1]]:  void *f3_handle
  void *f3_handle = dlopen("func3.so", RTLD_LAZY | RTLD_GLOBAL);
  if (f3_handle == NULL)
    return fprintf(stderr, "unable to open 'func3.so': %s\n", dlerror());
  void (*func3)(void) = (void (*)(void))dlsym(f3_handle, "func3");
  if (func3 == NULL)
    return fprintf(stderr, "unable to lookup symbol 'func3': %s\n", dlerror());
  func3();
#endif

  void (*gcov_reset1)() = (void (*)())dlsym(f1_handle, "__gcov_reset");
  if (gcov_reset1 == NULL)
    return fprintf(stderr, "unable to find __gcov_reset in func1.so': %s\n", dlerror());
  void (*gcov_reset2)() = (void (*)())dlsym(f2_handle, "__gcov_reset");
  if (gcov_reset2 == NULL)
    return fprintf(stderr, "unable to find __gcov_reset in func2.so': %s\n", dlerror());
  if (gcov_reset1 == gcov_reset2)
    return fprintf(stderr, "same __gcov_reset found in func1.so and func2.so\n");

  /// Test that __gcov_dump is in the dynamic symbol table.
  void (*gcov_dump1)() = (void (*)())dlsym(f1_handle, "__gcov_dump");
  if (gcov_dump1 == NULL)
    return fprintf(stderr, "unable to find __gcov_dump in func1.so': %s\n", dlerror());

  if (dlclose(f2_handle) != 0)
    return fprintf(stderr, "unable to close 'func2.so': %s\n", dlerror());

  func1();

  return 0;
}