1dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov#include <stdio.h>
2dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov#include <stdlib.h>
3dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov#include <unistd.h>
4dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov#include <string>
5dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov
6dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanovvoid usage(const char* me) {
7dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  static const char* usage_s = "Usage:\n"
8dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov    "  %s /system/bin/app_process <args>\n"
9dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov    "or, better:\n"
10dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov    "  setprop wrap.<nicename> %s\n";
11dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  fprintf(stderr, usage_s, me, me);
12dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  exit(1);
13dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov}
14dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov
15dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanovvoid env_prepend(const char* name, const char* value, const char* delim) {
16dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  const char* value_old = getenv(name);
17dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  std::string value_new = value;
18dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  if (value_old) {
19dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov    value_new += delim;
20dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov    value_new += value_old;
21dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  }
22dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  setenv(name, value_new.c_str(), 1);
23dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov}
24dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov
25dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanovint main(int argc, char** argv) {
26dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  if (argc < 2) {
27dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov    usage(argv[0]);
28dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  }
29dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  char** args = new char*[argc];
30dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  // If we are wrapping app_process, replace it with app_process_asan.
31dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  // TODO(eugenis): rewrite to <dirname>/asan/<basename>, if exists?
32dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  if (strcmp(argv[1], "/system/bin/app_process") == 0) {
33dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov    args[0] = (char*)"/system/bin/asan/app_process";
34dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  } else {
35dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov    args[0] = argv[1];
36dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  }
37dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov
38dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  for (int i = 1; i < argc - 1; ++i)
39dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov    args[i] = argv[i + 1];
40dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  args[argc - 1] = 0;
41dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov
42dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  env_prepend("ASAN_OPTIONS", "debug=1,verbosity=1", ",");
43dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  env_prepend("LD_LIBRARY_PATH", "/system/lib/asan", ":");
44dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  env_prepend("LD_PRELOAD", "/system/lib/libasan_preload.so", ":");
45dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov
46dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  printf("ASAN_OPTIONS: %s\n", getenv("ASAN_OPTIONS"));
47dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  printf("LD_LIBRARY_PATH: %s\n", getenv("LD_LIBRARY_PATH"));
48dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  printf("LD_PRELOAD: %s\n", getenv("LD_PRELOAD"));
49dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov
50dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov  execv(args[0], args);
51dc3865b01cd56b703b77f58d5acff6529491eaf3Evgeniy Stepanov}
52