| Juan Cespedes | 1c2be91 | 1997-06-09 01:12:01 +0200 | [diff] [blame] | 1 | #include <stdio.h> |
| Juan Cespedes | 23658aa | 1997-08-27 22:27:36 +0200 | [diff] [blame] | 2 | #include <stdlib.h> |
| 3 | #include <sys/param.h> |
| Juan Cespedes | 1c2be91 | 1997-06-09 01:12:01 +0200 | [diff] [blame] | 4 | #include <errno.h> |
| 5 | #include <unistd.h> |
| Juan Cespedes | 23658aa | 1997-08-27 22:27:36 +0200 | [diff] [blame] | 6 | #include <string.h> |
| Juan Cespedes | 1c2be91 | 1997-06-09 01:12:01 +0200 | [diff] [blame] | 7 | |
| Juan Cespedes | 96935a9 | 1997-08-09 23:45:39 +0200 | [diff] [blame] | 8 | #include "elf.h" |
| Juan Cespedes | ef04ba4 | 1997-08-22 21:55:45 +0200 | [diff] [blame] | 9 | #include "process.h" |
| Juan Cespedes | 3268a16 | 1997-08-25 16:45:22 +0200 | [diff] [blame] | 10 | #include "output.h" |
| Juan Cespedes | 96935a9 | 1997-08-09 23:45:39 +0200 | [diff] [blame] | 11 | |
| Juan Cespedes | 96935a9 | 1997-08-09 23:45:39 +0200 | [diff] [blame] | 12 | extern void read_config_file(const char *); |
| Juan Cespedes | 24c8253 | 1997-06-25 00:02:58 +0200 | [diff] [blame] | 13 | |
| Juan Cespedes | 5b2f981 | 1997-07-17 00:05:10 +0200 | [diff] [blame] | 14 | FILE * output = stderr; |
| Juan Cespedes | 5e4455b | 1997-08-24 01:48:26 +0200 | [diff] [blame] | 15 | int opt_d = 0; /* debug */ |
| 16 | int opt_i = 0; /* instruction pointer */ |
| 17 | int opt_S = 0; /* syscalls */ |
| Juan Cespedes | 5b2f981 | 1997-07-17 00:05:10 +0200 | [diff] [blame] | 18 | |
| Juan Cespedes | 5b2f981 | 1997-07-17 00:05:10 +0200 | [diff] [blame] | 19 | static void usage(void) |
| 20 | { |
| Juan Cespedes | 5e4455b | 1997-08-24 01:48:26 +0200 | [diff] [blame] | 21 | fprintf(stderr,"Usage: ltrace [-d] [-i] [-S] [-o filename] command [arg ...]\n\n"); |
| Juan Cespedes | 5b2f981 | 1997-07-17 00:05:10 +0200 | [diff] [blame] | 22 | } |
| 23 | |
| Juan Cespedes | 23658aa | 1997-08-27 22:27:36 +0200 | [diff] [blame] | 24 | static char * search_for_command(char * filename) |
| 25 | { |
| 26 | static char pathname[MAXPATHLEN]; |
| 27 | char *path; |
| 28 | int m, n; |
| 29 | |
| 30 | if (strchr(filename, '/')) { |
| 31 | return filename; |
| 32 | } |
| 33 | for (path = getenv("PATH"); path && *path; path += m) { |
| 34 | if (strchr(path, ':')) { |
| 35 | n = strchr(path, ':') - path; |
| 36 | m = n + 1; |
| 37 | } else { |
| 38 | m = n = strlen(path); |
| 39 | } |
| 40 | strncpy(pathname, path, n); |
| 41 | if (n && pathname[n - 1] != '/') { |
| 42 | pathname[n++] = '/'; |
| 43 | } |
| 44 | strcpy(pathname + n, filename); |
| 45 | if (!access(pathname, X_OK)) { |
| 46 | break; |
| 47 | } |
| 48 | } |
| 49 | if (access(pathname, X_OK)) { |
| 50 | return NULL; |
| 51 | } else { |
| 52 | return pathname; |
| 53 | } |
| 54 | } |
| 55 | |
| Juan Cespedes | 1c2be91 | 1997-06-09 01:12:01 +0200 | [diff] [blame] | 56 | int main(int argc, char **argv) |
| 57 | { |
| Juan Cespedes | ef04ba4 | 1997-08-22 21:55:45 +0200 | [diff] [blame] | 58 | int pid; |
| Juan Cespedes | 23658aa | 1997-08-27 22:27:36 +0200 | [diff] [blame] | 59 | char * command; |
| Juan Cespedes | ad78362 | 1997-06-10 17:11:33 +0200 | [diff] [blame] | 60 | |
| Juan Cespedes | 5b2f981 | 1997-07-17 00:05:10 +0200 | [diff] [blame] | 61 | while ((argc>2) && (argv[1][0] == '-') && (argv[1][2] == '\0')) { |
| Juan Cespedes | ad78362 | 1997-06-10 17:11:33 +0200 | [diff] [blame] | 62 | switch(argv[1][1]) { |
| Juan Cespedes | 1afec69 | 1997-08-23 21:31:46 +0200 | [diff] [blame] | 63 | case 'd': opt_d++; |
| Juan Cespedes | ad78362 | 1997-06-10 17:11:33 +0200 | [diff] [blame] | 64 | break; |
| Juan Cespedes | 5b2f981 | 1997-07-17 00:05:10 +0200 | [diff] [blame] | 65 | case 'o': output = fopen(argv[2], "w"); |
| 66 | if (!output) { |
| 67 | fprintf(stderr, "Can't open %s for output: %s\n", argv[2], sys_errlist[errno]); |
| 68 | exit(1); |
| 69 | } |
| 70 | argc--; argv++; |
| 71 | break; |
| Juan Cespedes | 1afec69 | 1997-08-23 21:31:46 +0200 | [diff] [blame] | 72 | case 'i': opt_i++; |
| 73 | break; |
| Juan Cespedes | 5e4455b | 1997-08-24 01:48:26 +0200 | [diff] [blame] | 74 | case 'S': opt_S++; |
| 75 | break; |
| Juan Cespedes | ad78362 | 1997-06-10 17:11:33 +0200 | [diff] [blame] | 76 | default: fprintf(stderr, "Unknown option '%c'\n", argv[1][1]); |
| Juan Cespedes | 5b2f981 | 1997-07-17 00:05:10 +0200 | [diff] [blame] | 77 | usage(); |
| Juan Cespedes | ad78362 | 1997-06-10 17:11:33 +0200 | [diff] [blame] | 78 | exit(1); |
| 79 | } |
| 80 | argc--; argv++; |
| 81 | } |
| Juan Cespedes | 1c2be91 | 1997-06-09 01:12:01 +0200 | [diff] [blame] | 82 | |
| 83 | if (argc<2) { |
| Juan Cespedes | 5b2f981 | 1997-07-17 00:05:10 +0200 | [diff] [blame] | 84 | usage(); |
| Juan Cespedes | 1c2be91 | 1997-06-09 01:12:01 +0200 | [diff] [blame] | 85 | exit(1); |
| 86 | } |
| Juan Cespedes | 23658aa | 1997-08-27 22:27:36 +0200 | [diff] [blame] | 87 | command = search_for_command(argv[1]); |
| 88 | if (!command) { |
| 89 | fprintf(stderr, "%s: command not found\n", argv[1]); |
| 90 | exit(1); |
| 91 | } |
| 92 | if (!read_elf(command)) { |
| 93 | fprintf(stderr, "%s: Not dynamically linked\n", command); |
| Juan Cespedes | 1c2be91 | 1997-06-09 01:12:01 +0200 | [diff] [blame] | 94 | exit(1); |
| 95 | } |
| Juan Cespedes | ef04ba4 | 1997-08-22 21:55:45 +0200 | [diff] [blame] | 96 | |
| Juan Cespedes | 1afec69 | 1997-08-23 21:31:46 +0200 | [diff] [blame] | 97 | if (opt_d>0) { |
| Juan Cespedes | 3268a16 | 1997-08-25 16:45:22 +0200 | [diff] [blame] | 98 | send_line("Reading config file(s)..."); |
| Juan Cespedes | 1afec69 | 1997-08-23 21:31:46 +0200 | [diff] [blame] | 99 | } |
| Juan Cespedes | 96935a9 | 1997-08-09 23:45:39 +0200 | [diff] [blame] | 100 | read_config_file("/etc/ltrace.cfg"); |
| 101 | read_config_file(".ltracerc"); |
| Juan Cespedes | 1afec69 | 1997-08-23 21:31:46 +0200 | [diff] [blame] | 102 | |
| Juan Cespedes | 23658aa | 1997-08-27 22:27:36 +0200 | [diff] [blame] | 103 | pid = execute_process(command, argv+1); |
| Juan Cespedes | 1afec69 | 1997-08-23 21:31:46 +0200 | [diff] [blame] | 104 | if (opt_d>0) { |
| Juan Cespedes | 3268a16 | 1997-08-25 16:45:22 +0200 | [diff] [blame] | 105 | send_line("pid %u launched", pid); |
| Juan Cespedes | 1afec69 | 1997-08-23 21:31:46 +0200 | [diff] [blame] | 106 | } |
| Juan Cespedes | ad78362 | 1997-06-10 17:11:33 +0200 | [diff] [blame] | 107 | |
| Juan Cespedes | 1c2be91 | 1997-06-09 01:12:01 +0200 | [diff] [blame] | 108 | while(1) { |
| Juan Cespedes | 3268a16 | 1997-08-25 16:45:22 +0200 | [diff] [blame] | 109 | wait_for_child(); |
| Juan Cespedes | 1c2be91 | 1997-06-09 01:12:01 +0200 | [diff] [blame] | 110 | } |
| Juan Cespedes | ef04ba4 | 1997-08-22 21:55:45 +0200 | [diff] [blame] | 111 | |
| Juan Cespedes | 1c2be91 | 1997-06-09 01:12:01 +0200 | [diff] [blame] | 112 | exit(0); |
| 113 | } |