ust: initial commit
[ust.git] / libtracectl / tracectl.c
1 #include <stdio.h>
2 #include <stdint.h>
3 #include <signal.h>
4 #include <sys/types.h>
5 #include <sys/socket.h>
6 #include <sys/un.h>
7 #define UNIX_PATH_MAX 108
8
9 //#define SOCKETDIR "/var/run/ust/socks"
10 #define SOCKETDIR "/tmp/socks"
11 #define SOCKETDIRLEN sizeof(SOCKETDIR)
12 #define USTSIGNAL SIGIO
13
14 #define DBG(fmt, args...) fprintf(stderr, fmt "\n", ## args)
15 #define WARN(fmt, args...) fprintf(stderr, "usertrace: WARNING: " fmt "\n", ## args)
16 #define ERR(fmt, args...) fprintf(stderr, "usertrace: ERROR: " fmt "\n", ## args)
17 #define PERROR(call) perror("usertrace: ERROR: " call)
18
19 struct tracecmd { /* no padding */
20 uint32_t size;
21 uint16_t command;
22 };
23
24
25 pid_t mypid;
26 char mysocketfile[UNIX_PATH_MAX] = "";
27
28 void do_command(struct tracecmd *cmd)
29 {
30 }
31
32 void receive_commands()
33 {
34 }
35
36 /* The signal handler itself. */
37
38 void sighandler(int sig)
39 {
40 DBG("sighandler");
41 receive_commands();
42 }
43
44 /* Called by the app signal handler to chain it to us. */
45
46 void chain_signal()
47 {
48 sighandler(USTSIGNAL);
49 }
50
51 int init_socket()
52 {
53 int result;
54 int fd;
55 char pidstr[6];
56 int pidlen;
57
58 struct sockaddr_un addr;
59
60 result = fd = socket(PF_UNIX, SOCK_SEQPACKET, 0);
61 if(result == -1) {
62 PERROR("socket");
63 return -1;
64 }
65
66 addr.sun_family = AF_UNIX;
67
68 result = snprintf(addr.sun_path, UNIX_PATH_MAX, "%s/%d", SOCKETDIR, mypid);
69 if(result >= UNIX_PATH_MAX) {
70 ERR("string overflow allocating socket name");
71 goto close_sock;
72 }
73 //DBG("opening socket at %s", addr.sun_path);
74
75 result = bind(fd, (struct sockaddr *)&addr, sizeof(addr));
76 if(result == -1) {
77 PERROR("bind");
78 goto close_sock;
79 }
80
81 strcpy(mysocketfile, addr.sun_path);
82
83 close_sock:
84 close(fd);
85
86 return -1;
87 }
88
89 void destroy_socket()
90 {
91 int result;
92
93 if(mysocketfile[0] == '\0')
94 return;
95
96 result = unlink(mysocketfile);
97 if(result == -1) {
98 PERROR("unlink");
99 }
100 }
101
102 int init_signal_handler(void)
103 {
104 /* Attempt to handler SIGIO. If the main program wants to
105 * handle it, fine, it'll override us. They it'll have to
106 * use the chaining function.
107 */
108
109 int result;
110 struct sigaction act;
111
112 result = sigemptyset(&act.sa_mask);
113 if(result == -1) {
114 PERROR("sigemptyset");
115 return -1;
116 }
117
118 act.sa_handler = sighandler;
119 act.sa_flags = SA_RESTART;
120
121 /* Only defer ourselves. Also, try to restart interrupted
122 * syscalls to disturb the traced program as little as possible.
123 */
124 result = sigaction(SIGIO, &act, NULL);
125 if(result == -1) {
126 PERROR("sigaction");
127 return -1;
128 }
129
130 return 0;
131 }
132
133 void __attribute__((constructor)) init()
134 {
135 int result;
136
137 mypid = getpid();
138
139 /* if using instead seperate thread, then should create thread */
140 result = init_signal_handler();
141 result = init_socket();
142
143 return;
144
145 /* should decrementally destroy stuff if error */
146
147 }
148
149 /* This is only called if we terminate normally, not with an unhandled signal,
150 * so we cannot rely on it. */
151
152 void __attribute__((destructor)) fini()
153 {
154 destroy_socket();
155 }
This page took 0.032484 seconds and 4 git commands to generate.