xref: /aosp_15_r20/system/core/debuggerd/pbtombstone.cpp (revision 00c7fec1bb09f3284aad6a6f96d2f63dfc3650ad)
1 /*
2  * Copyright (C) 2020 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #include <err.h>
18 #include <fcntl.h>
19 #include <getopt.h>
20 #include <stdio.h>
21 #include <unistd.h>
22 
23 #include <string>
24 #include <vector>
25 
26 #include <android-base/unique_fd.h>
27 #include <libdebuggerd/tombstone_proto_to_text.h>
28 
29 #include "tombstone.pb.h"
30 #include "tombstone_symbolize.h"
31 
32 using android::base::unique_fd;
33 
usage(bool error)34 [[noreturn]] void usage(bool error) {
35   fprintf(stderr, "usage: pbtombstone [OPTION] TOMBSTONE.PB\n");
36   fprintf(stderr, "Convert a protobuf tombstone to text.\n");
37   fprintf(stderr, "Arguments:\n");
38   fprintf(stderr, "  -h, --help                   print this message\n");
39   fprintf(stderr, "  --debug-file-directory PATH  specify the path to a symbols directory\n");
40   exit(error);
41 }
42 
main(int argc,char * argv[])43 int main(int argc, char* argv[]) {
44   std::vector<std::string> debug_file_directories;
45   static struct option long_options[] = {
46       {"debug-file-directory", required_argument, 0, 0},
47       {"help", no_argument, 0, 'h'},
48       {},
49   };
50   int c;
51   while ((c = getopt_long(argc, argv, "h", long_options, 0)) != -1) {
52     switch (c) {
53       case 0:
54         debug_file_directories.push_back(optarg);
55         break;
56 
57       case 'h':
58         usage(false);
59         break;
60     }
61   }
62 
63   if (optind != argc-1) {
64     usage(true);
65   }
66 
67   unique_fd fd(open(argv[optind], O_RDONLY | O_CLOEXEC));
68   if (fd == -1) {
69     err(1, "failed to open tombstone '%s'", argv[1]);
70   }
71 
72   Tombstone tombstone;
73   if (!tombstone.ParseFromFileDescriptor(fd.get())) {
74     err(1, "failed to parse tombstone");
75   }
76 
77   Symbolizer sym;
78   sym.Start(debug_file_directories);
79   bool result = tombstone_proto_to_text(
80       tombstone, [](const std::string& line, bool) { printf("%s\n", line.c_str()); },
81       [&](const BacktraceFrame& frame) { symbolize_backtrace_frame(frame, sym); });
82 
83   if (!result) {
84     errx(1, "tombstone was malformed");
85   }
86 
87   return 0;
88 }
89