xref: /freebsd/contrib/llvm-project/openmp/runtime/src/ompd-specific.cpp (revision fe6060f10f634930ff71b7c50291ddc610da2475)
1  /*
2   * ompd-specific.cpp -- OpenMP debug support
3   */
4  
5  //===----------------------------------------------------------------------===//
6  //
7  // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
8  // See https://llvm.org/LICENSE.txt for license information.
9  // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
10  //
11  //===----------------------------------------------------------------------===//
12  
13  #include "ompd-specific.h"
14  
15  #if OMPD_SUPPORT
16  
17  /**
18   * Declaration of symbols to hold struct size and member offset information
19   */
20  
21  #define ompd_declare_access(t, m) uint64_t ompd_access__##t##__##m;
22  OMPD_FOREACH_ACCESS(ompd_declare_access)
23  #undef ompd_declare_access
24  
25  #define ompd_declare_sizeof_member(t, m) uint64_t ompd_sizeof__##t##__##m;
26  OMPD_FOREACH_ACCESS(ompd_declare_sizeof_member)
27  #undef ompd_declare_sizeof_member
28  
29  #define ompd_declare_bitfield(t, m) uint64_t ompd_bitfield__##t##__##m;
30  OMPD_FOREACH_BITFIELD(ompd_declare_bitfield)
31  #undef ompd_declare_bitfield
32  
33  #define ompd_declare_sizeof(t) uint64_t ompd_sizeof__##t;
34  OMPD_FOREACH_SIZEOF(ompd_declare_sizeof)
35  #undef ompd_declare_sizeof
36  
37  volatile const char **ompd_dll_locations = NULL;
38  uint64_t ompd_state = 0;
39  
40  char *ompd_env_block = NULL;
41  ompd_size_t ompd_env_block_size = 0;
42  
ompd_init()43  void ompd_init() {
44  
45    static int ompd_initialized = 0;
46  
47    if (ompd_initialized)
48      return;
49  
50      /**
51       * Calculate member offsets for structs and unions
52       */
53  
54  #define ompd_init_access(t, m)                                                 \
55    ompd_access__##t##__##m = (uint64_t) & (((t *)0)->m);
56    OMPD_FOREACH_ACCESS(ompd_init_access)
57  #undef ompd_init_access
58  
59    /**
60     * Create bit mask for bitfield access
61     */
62  
63  #define ompd_init_bitfield(t, m)                                               \
64    ompd_bitfield__##t##__##m = 0;                                               \
65    ((t *)(&ompd_bitfield__##t##__##m))->m = 1;
66    OMPD_FOREACH_BITFIELD(ompd_init_bitfield)
67  #undef ompd_init_bitfield
68  
69    /**
70     * Calculate type size information
71     */
72  
73  #define ompd_init_sizeof_member(t, m)                                          \
74    ompd_sizeof__##t##__##m = sizeof(((t *)0)->m);
75    OMPD_FOREACH_ACCESS(ompd_init_sizeof_member)
76  #undef ompd_init_sizeof_member
77  
78  #define ompd_init_sizeof(t) ompd_sizeof__##t = sizeof(t);
79    OMPD_FOREACH_SIZEOF(ompd_init_sizeof)
80  #undef ompd_init_sizeof
81  
82    char *libname = NULL;
83  
84  #if KMP_OS_UNIX
85    // Find the location of libomp.so thru dladdr and replace the libomp with
86    // libompd to get the full path of libompd
87    Dl_info dl_info;
88    int ret = dladdr((void *)ompd_init, &dl_info);
89    if (!ret) {
90      fprintf(stderr, "%s\n", dlerror());
91    }
92    int lib_path_length;
93    if (strrchr(dl_info.dli_fname, '/')) {
94      lib_path_length = strrchr(dl_info.dli_fname, '/') - dl_info.dli_fname;
95      libname =
96          (char *)malloc(lib_path_length + 12 /*for '/libompd.so' and '\0'*/);
97      strncpy(libname, dl_info.dli_fname, lib_path_length);
98      memcpy(libname + lib_path_length, "/libompd.so\0", 12);
99    }
100  #endif
101  
102    const char *ompd_env_var = getenv("OMP_DEBUG");
103    if (ompd_env_var && !strcmp(ompd_env_var, "enabled")) {
104      fprintf(stderr, "OMP_OMPD active\n");
105      ompt_enabled.enabled = 1;
106      ompd_state |= OMPD_ENABLE_BP;
107    }
108  
109    ompd_initialized = 1;
110    ompd_dll_locations = (volatile const char **)malloc(3 * sizeof(const char *));
111    ompd_dll_locations[0] = "libompd.so";
112    ompd_dll_locations[1] = libname;
113    ompd_dll_locations[2] = NULL;
114    ompd_dll_locations_valid();
115  }
116  
ompd_dll_locations_valid(void)117  void __attribute__((noinline)) ompd_dll_locations_valid(void) {
118    /* naive way of implementing hard to opt-out empty function
119       we might want to use a separate object file? */
120    asm("");
121  }
122  
ompd_bp_parallel_begin(void)123  void ompd_bp_parallel_begin(void) {
124    /* naive way of implementing hard to opt-out empty function
125       we might want to use a separate object file? */
126    asm("");
127  }
ompd_bp_parallel_end(void)128  void ompd_bp_parallel_end(void) {
129    /* naive way of implementing hard to opt-out empty function
130       we might want to use a separate object file? */
131    asm("");
132  }
ompd_bp_task_begin(void)133  void ompd_bp_task_begin(void) {
134    /* naive way of implementing hard to opt-out empty function
135       we might want to use a separate object file? */
136    asm("");
137  }
ompd_bp_task_end(void)138  void ompd_bp_task_end(void) {
139    /* naive way of implementing hard to opt-out empty function
140       we might want to use a separate object file? */
141    asm("");
142  }
ompd_bp_thread_begin(void)143  void ompd_bp_thread_begin(void) {
144    /* naive way of implementing hard to opt-out empty function
145       we might want to use a separate object file? */
146    asm("");
147  }
ompd_bp_thread_end(void)148  void ompd_bp_thread_end(void) {
149    /* naive way of implementing hard to opt-out empty function
150       we might want to use a separate object file? */
151    asm("");
152  }
153  
154  #endif /* OMPD_SUPPORT */
155