Daniel Tang commited on
Commit
82ee857
·
1 Parent(s): 90d9ecb

ggml : Fix missing backtrace on Linux (ggml/1228)

Browse files

* Modern Linux defaults /proc/sys/kernel/yama/ptrace_scope to 1
* Fixed lldb attach
* Simplify by having the child do ggml_print_backtrace_symbols

Files changed (1) hide show
  1. ggml/src/ggml.c +44 -15
ggml/src/ggml.c CHANGED
@@ -70,6 +70,9 @@ float ggml_table_f32_f16[1 << 16];
70
  #include <sys/types.h>
71
  #include <sys/stat.h>
72
  #include <sys/wait.h>
 
 
 
73
 
74
  #if defined(__ANDROID__)
75
  #include <unwind.h>
@@ -133,10 +136,36 @@ static void ggml_print_backtrace(void) {
133
  if (GGML_NO_BACKTRACE) {
134
  return;
135
  }
136
- char attach[32];
137
- snprintf(attach, sizeof(attach), "attach %d", getpid());
138
- int pid = fork();
139
- if (pid == 0) {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
140
  // try gdb
141
  execlp("gdb", "gdb", "--batch",
142
  "-ex", "set style enabled on",
@@ -149,18 +178,18 @@ static void ggml_print_backtrace(void) {
149
  execlp("lldb", "lldb", "--batch",
150
  "-o", "bt",
151
  "-o", "quit",
152
- "-p", attach,
153
  (char *) NULL);
154
- exit(EXIT_FAILURE);
155
- } else {
156
- int wstatus;
157
- waitpid(pid, &wstatus, 0);
158
- if (WIFEXITED(wstatus)) {
159
- if (WEXITSTATUS(wstatus) == EXIT_FAILURE) {
160
- // gdb failed, fallback to backtrace_symbols
161
- ggml_print_backtrace_symbols();
162
- }
163
- }
164
  }
165
  }
166
  #else
 
70
  #include <sys/types.h>
71
  #include <sys/stat.h>
72
  #include <sys/wait.h>
73
+ #if defined(__linux__)
74
+ #include <sys/prctl.h>
75
+ #endif
76
 
77
  #if defined(__ANDROID__)
78
  #include <unwind.h>
 
136
  if (GGML_NO_BACKTRACE) {
137
  return;
138
  }
139
+ #if defined(__linux__)
140
+ FILE * f = fopen("/proc/self/status", "r");
141
+ size_t size = 0;
142
+ char * line = NULL;
143
+ ssize_t length = 0;
144
+ while ((length = getline(&line, &size, f)) > 0) {
145
+ if (!strncmp(line, "TracerPid:", sizeof("TracerPid:") - 1) &&
146
+ (length != sizeof("TracerPid:\t0\n") - 1 || line[length - 2] != '0')) {
147
+ // Already being debugged, and the breakpoint is the later abort()
148
+ free(line);
149
+ fclose(f);
150
+ return;
151
+ }
152
+ }
153
+ free(line);
154
+ fclose(f);
155
+ int lock[2] = { -1, -1 };
156
+ (void) !pipe(lock); // Don't start gdb until after PR_SET_PTRACER
157
+ #endif
158
+ const int parent_pid = getpid();
159
+ const int child_pid = fork();
160
+ if (child_pid < 0) { // error
161
+ return;
162
+ } else if (child_pid == 0) { // child
163
+ char attach[32];
164
+ snprintf(attach, sizeof(attach), "attach %d", parent_pid);
165
+ #if defined(__linux__)
166
+ close(lock[1]);
167
+ (void) !read(lock[0], lock, 1);
168
+ #endif
169
  // try gdb
170
  execlp("gdb", "gdb", "--batch",
171
  "-ex", "set style enabled on",
 
178
  execlp("lldb", "lldb", "--batch",
179
  "-o", "bt",
180
  "-o", "quit",
181
+ "-p", &attach[sizeof("attach ") - 1],
182
  (char *) NULL);
183
+ // gdb failed, fallback to backtrace_symbols
184
+ ggml_print_backtrace_symbols();
185
+ _Exit(0);
186
+ } else { // parent
187
+ #if defined(__linux__)
188
+ prctl(PR_SET_PTRACER, child_pid);
189
+ close(lock[1]);
190
+ close(lock[0]);
191
+ #endif
192
+ waitpid(child_pid, NULL, 0);
193
  }
194
  }
195
  #else