dumpsys: make timeout value an argument
Also rework the args parsing using getopt_long.
Bug: 27788406
Change-Id: I60fd8e614616334d47b8de574f3c81a121a6ac0a
Signed-off-by: Thierry Strudel <tstrudel@google.com>
diff --git a/cmds/dumpstate/dumpstate.cpp b/cmds/dumpstate/dumpstate.cpp
index 356b68f..b391d76 100644
--- a/cmds/dumpstate/dumpstate.cpp
+++ b/cmds/dumpstate/dumpstate.cpp
@@ -881,10 +881,7 @@
printf("== Android Framework Services\n");
printf("========================================================\n");
- /* the full dumpsys is starting to take a long time, so we need
- to increase its timeout. we really need to do the timeouts in
- dumpsys itself... */
- run_command("DUMPSYS", 60, "dumpsys", "--skip", "meminfo,cpuinfo", NULL);
+ run_command("DUMPSYS", 60, "dumpsys", "-t", "60", "--skip", "meminfo,cpuinfo", NULL);
printf("========================================================\n");
printf("== Checkins\n");
@@ -1250,8 +1247,8 @@
// Invoking the following dumpsys calls before dump_traces() to try and
// keep the system stats as close to its initial state as possible.
- run_command_as_shell("DUMPSYS MEMINFO", 30, "dumpsys", "meminfo", "-a", NULL);
- run_command_as_shell("DUMPSYS CPUINFO", 30, "dumpsys", "cpuinfo", "-a", NULL);
+ run_command_as_shell("DUMPSYS MEMINFO", 30, "dumpsys", "-t", "30", "meminfo", "-a", NULL);
+ run_command_as_shell("DUMPSYS CPUINFO", 10, "dumpsys", "cpuinfo", "-a", NULL);
/* collect stack traces from Dalvik and native processes (needs root) */
dump_traces_path = dump_traces();
diff --git a/cmds/dumpsys/dumpsys.cpp b/cmds/dumpsys/dumpsys.cpp
index 003fcc3..db06e99 100644
--- a/cmds/dumpsys/dumpsys.cpp
+++ b/cmds/dumpsys/dumpsys.cpp
@@ -43,9 +43,10 @@
"usage: dumpsys\n"
" To dump all services.\n"
"or:\n"
- " dumpsys [--help | -l | --skip SERVICES | SERVICE [ARGS]]\n"
+ " dumpsys [-t TIMEOUT] [--help | -l | --skip SERVICES | SERVICE [ARGS]]\n"
" --help: shows this help\n"
" -l: only list services, do not dump them\n"
+ " -t TIMEOUT: TIMEOUT to use in seconds instead of default 10 seconds\n"
" --skip SERVICES: dumps all services but SERVICES (comma-separated list)\n"
" SERVICE [ARGS]: dumps only service SERVICE, optionally passing ARGS to it\n");
}
@@ -74,44 +75,80 @@
Vector<String16> args;
Vector<String16> skippedServices;
bool showListOnly = false;
- if (argc == 2) {
- // 1 argument: check for special cases (-l or --help)
- if (strcmp(argv[1], "--help") == 0) {
- usage();
- return 0;
+ bool skipServices = false;
+ int timeoutArg = 10;
+ static struct option longOptions[] = {
+ {"skip", no_argument, 0, 0 },
+ {"help", no_argument, 0, 0 },
+ { 0, 0, 0, 0 }
+ };
+
+ while (1) {
+ int c;
+ int optionIndex = 0;
+
+ c = getopt_long(argc, argv, "+t:l", longOptions, &optionIndex);
+
+ if (c == -1) {
+ break;
}
- if (strcmp(argv[1], "-l") == 0) {
+
+ switch (c) {
+ case 0:
+ if (!strcmp(longOptions[optionIndex].name, "skip")) {
+ skipServices = true;
+ } else if (!strcmp(longOptions[optionIndex].name, "help")) {
+ usage();
+ return 0;
+ }
+ break;
+
+ case 't':
+ {
+ char *endptr;
+ timeoutArg = strtol(optarg, &endptr, 10);
+ if (*endptr != '\0' || timeoutArg <= 0) {
+ fprintf(stderr, "Error: invalid timeout number: '%s'\n", optarg);
+ return -1;
+ }
+ }
+ break;
+
+ case 'l':
showListOnly = true;
+ break;
+
+ default:
+ fprintf(stderr, "\n");
+ usage();
+ return -1;
}
}
- if (argc == 3) {
- // 2 arguments: check for special cases (--skip SERVICES)
- if (strcmp(argv[1], "--skip") == 0) {
- char* token = strtok(argv[2], ",");
- while (token != NULL) {
- skippedServices.add(String16(token));
- token = strtok(NULL, ",");
+
+ for (int i = optind; i < argc; i++) {
+ if (skipServices) {
+ skippedServices.add(String16(argv[i]));
+ } else {
+ if (i == optind) {
+ services.add(String16(argv[i]));
+ } else {
+ args.add(String16(argv[i]));
}
}
}
- bool dumpAll = argc == 1;
- if (dumpAll || !skippedServices.empty() || showListOnly) {
+
+ if ((skipServices && skippedServices.empty()) ||
+ (!skipServices && !showListOnly && services.empty()) ||
+ (showListOnly && (!services.empty() || !skippedServices.empty()))) {
+ usage();
+ return -1;
+ }
+
+ if (!skippedServices.empty() || showListOnly) {
// gets all services
services = sm->listServices();
services.sort(sort_func);
args.add(String16("-a"));
- } else {
- // gets a specific service:
- // first check if its name is not a special argument...
- if (strcmp(argv[1], "--skip") == 0 || strcmp(argv[1], "-l") == 0) {
- usage();
- return -1;
- }
- // ...then gets its arguments
- services.add(String16(argv[1]));
- for (int i=2; i<argc; i++) {
- args.add(String16(argv[i]));
- }
}
const size_t N = services.size();
@@ -173,8 +210,7 @@
}
});
- // TODO: Make this configurable at runtime.
- constexpr auto timeout = std::chrono::seconds(10);
+ auto timeout = std::chrono::seconds(timeoutArg);
auto end = std::chrono::steady_clock::now() + timeout;
struct pollfd pfd = {