]> granicus.if.org Git - strace/blob - ipc.c
Fix signed/unsigned problems
[strace] / ipc.c
1 /*
2  * Copyright (c) 1993 Ulrich Pegelow <pegelow@moorea.uni-muenster.de>
3  * Copyright (c) 1993 Branko Lankester <branko@hacktic.nl>
4  * Copyright (c) 1993, 1994, 1995, 1996 Rick Sladkey <jrs@world.std.com>
5  * Copyright (c) 1996-1999 Wichert Akkerman <wichert@cistron.nl>
6  * All rights reserved.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  * 3. The name of the author may not be used to endorse or promote products
17  *    derived from this software without specific prior written permission.
18  *
19  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
20  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
21  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
22  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
23  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
24  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
28  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29  *
30  *      $Id$
31  */
32
33 #include "defs.h"
34
35 #if defined(LINUX) || defined(SUNOS4) || defined(FREEBSD)
36
37 #include <sys/ipc.h>
38 #include <sys/sem.h>
39 #include <sys/msg.h>
40 #include <sys/shm.h>
41
42 #ifndef MSG_STAT
43 #define MSG_STAT 11
44 #endif
45 #ifndef MSG_INFO
46 #define MSG_INFO 12
47 #endif
48 #ifndef SHM_STAT
49 #define SHM_STAT 13
50 #endif
51 #ifndef SHM_INFO
52 #define SHM_INFO 14
53 #endif
54 #ifndef SEM_STAT
55 #define SEM_STAT 18
56 #endif
57 #ifndef SEM_INFO
58 #define SEM_INFO 19
59 #endif
60
61 static struct xlat msgctl_flags[] = {
62         { IPC_RMID,     "IPC_RMID"      },
63         { IPC_SET,      "IPC_SET"       },
64         { IPC_STAT,     "IPC_STAT"      },
65 #ifdef LINUX
66         { IPC_INFO,     "IPC_INFO"      },
67         { MSG_STAT,     "MSG_STAT"      },
68         { MSG_INFO,     "MSG_INFO"      },
69 #endif /* LINUX */
70         { 0,            NULL            },
71 };
72
73 static struct xlat semctl_flags[] = {
74         { IPC_RMID,     "IPC_RMID"      },
75         { IPC_SET,      "IPC_SET"       },
76         { IPC_STAT,     "IPC_STAT"      },
77 #ifdef LINUX
78         { IPC_INFO,     "IPC_INFO"      },
79         { SEM_STAT,     "SEM_STAT"      },
80         { SEM_INFO,     "SEM_INFO"      },
81 #endif /* LINUX */
82         { GETPID,       "GETPID"        },
83         { GETVAL,       "GETVAL"        },
84         { GETALL,       "GETALL"        },
85         { GETNCNT,      "GETNCNT"       },
86         { GETZCNT,      "GETZCNT"       },
87         { SETVAL,       "SETVAL"        },
88         { SETALL,       "SETALL"        },
89         { 0,            NULL            },
90 };
91
92 static struct xlat shmctl_flags[] = {
93         { IPC_RMID,     "IPC_RMID"      },
94         { IPC_SET,      "IPC_SET"       },
95         { IPC_STAT,     "IPC_STAT"      },
96 #ifdef LINUX
97         { IPC_INFO,     "IPC_INFO"      },
98         { SHM_STAT,     "SHM_STAT"      },
99         { SHM_INFO,     "SHM_INFO"      },
100 #endif /* LINUX */
101 #ifdef SHM_LOCK 
102         { SHM_LOCK,     "SHM_LOCK"      },
103 #endif
104 #ifdef SHM_UNLOCK       
105         { SHM_UNLOCK,   "SHM_UNLOCK"    },
106 #endif  
107         { 0,            NULL            },
108 };
109
110 static struct xlat resource_flags[] = {
111         { IPC_CREAT,    "IPC_CREAT"     },
112         { IPC_EXCL,     "IPC_EXCL"      },
113         { IPC_NOWAIT,   "IPC_NOWAIT"    },
114         { 0,            NULL            },
115 };
116
117 static struct xlat shm_flags[] = {
118 #ifdef LINUX
119         { SHM_REMAP,    "SHM_REMAP"     },
120 #endif /* LINUX */
121         { SHM_RDONLY,   "SHM_RDONLY"    },
122         { SHM_RND,      "SHM_RND"       },
123         { 0,            NULL            },
124 };
125
126 static struct xlat msg_flags[] = {
127         { MSG_NOERROR,  "MSG_NOERROR"   },
128 #ifdef LINUX
129         { MSG_EXCEPT,   "MSG_EXCEPT"    },
130 #endif /* LINUX */
131         { IPC_NOWAIT,   "IPC_NOWAIT"    },
132         { 0,            NULL            },
133 };
134
135 int sys_msgget(tcp)
136 struct tcb *tcp;
137 {
138         if (entering(tcp)) {
139                 if (tcp->u_arg[0])
140                         tprintf("%lu", tcp->u_arg[0]);
141                 else
142                         tprintf("IPC_PRIVATE");
143                 tprintf(", ");
144                 if (printflags(resource_flags, tcp->u_arg[1]) != 0)
145                         tprintf("|");
146                 tprintf("%#lo", tcp->u_arg[1] & 0666);
147         }
148         return 0;
149 }
150
151 int sys_msgctl(tcp)
152 struct tcb *tcp;
153 {
154         char *cmd = xlookup(msgctl_flags, tcp->u_arg[1]);
155
156         if (entering(tcp)) {
157                 tprintf("%lu", tcp->u_arg[0]);
158                 tprintf(", %s", cmd == NULL ? "MSG_???" : cmd);
159 #ifdef LINUX
160                 tprintf(", %#lx", tcp->u_arg[3]);
161 #else /* !LINUX */
162                 tprintf(", %#lx", tcp->u_arg[2]);
163 #endif /* !LINUX */
164         }
165         return 0;
166 }
167
168 int sys_msgsnd(tcp)
169 struct tcb *tcp;
170 {
171         long mtype;
172
173         if (entering(tcp)) {
174                 tprintf("%lu", tcp->u_arg[0]);
175 #ifdef LINUX
176                 umove(tcp, tcp->u_arg[3], &mtype);
177                 tprintf(", {%lu, ", mtype);
178                 printstr(tcp, tcp->u_arg[3] + sizeof(long),
179                         tcp->u_arg[1]);
180                 tprintf("}, %lu", tcp->u_arg[1]);
181                 tprintf(", ");
182                 if (printflags(msg_flags, tcp->u_arg[2]) == 0)
183                         tprintf("0");
184 #else /* !LINUX */
185                 umove(tcp, tcp->u_arg[1], &mtype);
186                 tprintf(", {%lu, ", mtype);
187                 printstr(tcp, tcp->u_arg[1] + sizeof(long),
188                         tcp->u_arg[2]);
189                 tprintf("}, %lu", tcp->u_arg[2]);
190                 tprintf(", ");
191                 if (printflags(msg_flags, tcp->u_arg[3]) == 0)
192                         tprintf("0");
193 #endif /* !LINUX */
194         }
195         return 0;
196 }
197
198 int sys_msgrcv(tcp)
199 struct tcb *tcp;
200 {
201         long mtype;
202 #ifdef LINUX
203         struct ipc_wrapper {
204                 struct msgbuf *msgp;
205                 long msgtyp;
206         } tmp;
207 #endif
208
209
210         if (exiting(tcp)) {
211                 tprintf("%lu", tcp->u_arg[0]);
212 #ifdef LINUX
213                 umove(tcp, tcp->u_arg[3], &tmp);
214                 umove(tcp, (long) tmp.msgp, &mtype);
215                 tprintf(", {%lu, ", mtype);
216                 printstr(tcp, (long) (tmp.msgp) + sizeof(long),
217                         tcp->u_arg[1]);
218                 tprintf("}, %lu", tcp->u_arg[1]);
219                 tprintf(", %ld", tmp.msgtyp);
220                 tprintf(", ");
221                 if (printflags(msg_flags, tcp->u_arg[2]) == 0)
222                         tprintf("0");
223 #else /* !LINUX */
224                 umove(tcp, tcp->u_arg[1], &mtype);
225                 tprintf(", {%lu, ", mtype);
226                 printstr(tcp, tcp->u_arg[1] + sizeof(long),
227                         tcp->u_arg[2]);
228                 tprintf("}, %lu", tcp->u_arg[2]);
229                 tprintf(", %ld", tcp->u_arg[3]);
230                 tprintf(", ");
231                 if (printflags(msg_flags, tcp->u_arg[4]) == 0)
232                         tprintf("0");
233 #endif /* !LINUX */
234         }
235         return 0;
236 }
237
238 int sys_semop(tcp)
239 struct tcb *tcp;
240 {
241         if (entering(tcp)) {
242                 tprintf("%lu", tcp->u_arg[0]);
243 #ifdef LINUX
244                 tprintf(", %#lx", tcp->u_arg[3]);
245                 tprintf(", %lu", tcp->u_arg[1]);
246 #else /* !LINUX */
247                 tprintf(", %#lx", tcp->u_arg[1]);
248                 tprintf(", %lu", tcp->u_arg[2]);
249 #endif /* !LINUX */
250         }
251         return 0;
252 }
253
254 int sys_semget(tcp)
255 struct tcb *tcp;
256 {
257         if (entering(tcp)) {
258                 if (tcp->u_arg[0])
259                         tprintf("%lu", tcp->u_arg[0]);
260                 else
261                         tprintf("IPC_PRIVATE");
262                 tprintf(", %lu", tcp->u_arg[1]);
263                 tprintf(", ");
264                 if (printflags(resource_flags, tcp->u_arg[2]) != 0)
265                         tprintf("|");
266                 tprintf("%#lo", tcp->u_arg[2] & 0666);
267         }
268         return 0;
269 }
270
271 int sys_semctl(tcp)
272 struct tcb *tcp;
273 {
274         if (entering(tcp)) {
275                 tprintf("%lu", tcp->u_arg[0]);
276                 tprintf(", %lu, ", tcp->u_arg[1]);
277                 printxval(semctl_flags, tcp->u_arg[2], "SEM_???");
278                 tprintf(", %#lx", tcp->u_arg[3]);
279         }
280         return 0;
281 }
282
283 int sys_shmget(tcp)
284 struct tcb *tcp;
285 {
286         if (entering(tcp)) {
287                 if (tcp->u_arg[0])
288                         tprintf("%lu", tcp->u_arg[0]);
289                 else
290                         tprintf("IPC_PRIVATE");
291                 tprintf(", %lu", tcp->u_arg[1]);
292                 tprintf(", ");
293                 if (printflags(resource_flags, tcp->u_arg[2]) != 0)
294                         tprintf("|");
295                 tprintf("%#lo", tcp->u_arg[2] & 0666);
296         }
297         return 0;
298 }
299
300 int sys_shmctl(tcp)
301 struct tcb *tcp;
302 {
303         if (entering(tcp)) {
304                 tprintf("%lu, ", tcp->u_arg[0]);
305                 printxval(shmctl_flags, tcp->u_arg[1], "SHM_???");
306 #ifdef LINUX
307                 tprintf(", %#lx", tcp->u_arg[3]);
308 #else /* !LINUX */
309                 tprintf(", %#lx", tcp->u_arg[2]);
310 #endif /* !LINUX */
311         }
312         return 0;
313 }
314
315 int sys_shmat(tcp)
316 struct tcb *tcp;
317 {
318 #ifdef LINUX
319         unsigned long raddr;
320 #endif /* LINUX */
321
322         if (exiting(tcp)) {
323                 tprintf("%lu", tcp->u_arg[0]);
324 #ifdef LINUX
325                 tprintf(", %#lx", tcp->u_arg[3]);
326                 tprintf(", ");
327                 if (printflags(shm_flags, tcp->u_arg[1]) == 0)
328                         tprintf("0");
329 #else /* !LINUX */
330                 tprintf(", %#lx", tcp->u_arg[1]);
331                 tprintf(", ");
332                 if (printflags(shm_flags, tcp->u_arg[2]) == 0)
333                         tprintf("0");
334 #endif /* !LINUX */
335                 if (syserror(tcp))
336                         return 0;
337 #ifdef LINUX
338                 if (umove(tcp, tcp->u_arg[2], &raddr) < 0)
339                         return RVAL_NONE;
340                 tcp->u_rval = raddr;
341 #endif /* LINUX */
342                 return RVAL_HEX;
343         }
344         return 0;
345 }
346
347 int sys_shmdt(tcp)
348 struct tcb *tcp;
349 {
350         if (entering(tcp))
351 #ifdef LINUX
352                 tprintf("%#lx", tcp->u_arg[3]);
353 #else /* !LINUX */
354                 tprintf("%#lx", tcp->u_arg[0]);
355 #endif /* !LINUX */
356         return 0;
357 }
358
359 #endif /* defined(LINUX) || defined(SUNOS4) || defined(FREEBSD) */