OSDN Git Service

Merge tree-ssa-20020619-branch into mainline.
[pf3gnuchains/gcc-fork.git] / libmudflap / mf-hooks2.c
1 /* Mudflap: narrow-pointer bounds-checking by tree rewriting.
2    Copyright (C) 2002, 2003 Free Software Foundation, Inc.
3    Contributed by Frank Ch. Eigler <fche@redhat.com>
4    and Graydon Hoare <graydon@redhat.com>
5
6 This file is part of GCC.
7
8 GCC is free software; you can redistribute it and/or modify it under
9 the terms of the GNU General Public License as published by the Free
10 Software Foundation; either version 2, or (at your option) any later
11 version.
12
13 In addition to the permissions in the GNU General Public License, the
14 Free Software Foundation gives you unlimited permission to link the
15 compiled version of this file into combinations with other programs,
16 and to distribute those combinations without any restriction coming
17 from the use of this file.  (The General Public License restrictions
18 do apply in other respects; for example, they cover modification of
19 the file, and distribution when not linked into a combine
20 executable.)
21
22 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
23 WARRANTY; without even the implied warranty of MERCHANTABILITY or
24 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
25 for more details.
26
27 You should have received a copy of the GNU General Public License
28 along with GCC; see the file COPYING.  If not, write to the Free
29 Software Foundation, 59 Temple Place - Suite 330, Boston, MA
30 02111-1307, USA.  */
31
32
33 #include "config.h"
34
35 #ifndef HAVE_SOCKLEN_T
36 #define socklen_t int
37 #endif
38
39 /* These attempt to coax various unix flavours to declare all our
40    needed tidbits in the system headers.  */
41 #if !defined(__FreeBSD__) && !defined(__APPLE__)
42 #define _POSIX_SOURCE
43 #endif /* Some BSDs break <sys/socket.h> if this is defined. */
44 #define _GNU_SOURCE 
45 #define _XOPEN_SOURCE
46 #define _BSD_TYPES
47 #define __EXTENSIONS__
48 #define _ALL_SOURCE
49 #define _LARGE_FILE_API
50 #define _XOPEN_SOURCE_EXTENDED 1
51
52 #include <string.h>
53 #include <strings.h>
54 #include <stdio.h>
55 #include <stdlib.h>
56 #include <sys/time.h>
57 #include <sys/types.h>
58 #include <unistd.h>
59 #include <assert.h>
60 #include <errno.h>
61 #include <limits.h>
62 #include <time.h>
63
64 #include "mf-runtime.h"
65 #include "mf-impl.h"
66
67 #ifdef _MUDFLAP
68 #error "Do not compile this file with -fmudflap!"
69 #endif
70
71
72 /* A bunch of independent stdlib/unistd hook functions, all
73    intercepted by mf-runtime.h macros.  */
74
75 #ifdef __FreeBSD__
76 #undef WRAP_memrchr
77 #undef WRAP_memmem
78 #include <dlfcn.h>
79 static inline size_t (strnlen) (const char* str, size_t n)
80 {
81   const char *s;
82
83   for (s = str; n && *s; ++s, --n)
84     ;
85   return (s - str);
86 }
87 #endif
88
89 /* str*,mem*,b* */
90
91 #ifdef WRAP_memcpy
92 WRAPPER2(void *, memcpy, void *dest, const void *src, size_t n)
93 {
94   TRACE ("%s\n", __PRETTY_FUNCTION__);
95   MF_VALIDATE_EXTENT(src, n, __MF_CHECK_READ, "memcpy source");
96   MF_VALIDATE_EXTENT(dest, n, __MF_CHECK_WRITE, "memcpy dest");
97   return memcpy (dest, src, n);
98 }
99 #endif
100
101
102 #ifdef WRAP_memmove
103 WRAPPER2(void *, memmove, void *dest, const void *src, size_t n)
104 {
105   TRACE ("%s\n", __PRETTY_FUNCTION__);
106   MF_VALIDATE_EXTENT(src, n, __MF_CHECK_READ, "memmove src");
107   MF_VALIDATE_EXTENT(dest, n, __MF_CHECK_WRITE, "memmove dest");
108   return memmove (dest, src, n);
109 }
110 #endif
111
112 #ifdef WRAP_memset
113 WRAPPER2(void *, memset, void *s, int c, size_t n)
114 {
115   TRACE ("%s\n", __PRETTY_FUNCTION__);
116   MF_VALIDATE_EXTENT(s, n, __MF_CHECK_WRITE, "memset dest");
117   return memset (s, c, n);
118 }
119 #endif
120
121 #ifdef WRAP_memcmp
122 WRAPPER2(int, memcmp, const void *s1, const void *s2, size_t n)
123 {
124   TRACE ("%s\n", __PRETTY_FUNCTION__);
125   MF_VALIDATE_EXTENT(s1, n, __MF_CHECK_READ, "memcmp 1st arg");
126   MF_VALIDATE_EXTENT(s2, n, __MF_CHECK_READ, "memcmp 2nd arg");
127   return memcmp (s1, s2, n);
128 }
129 #endif
130
131 #ifdef WRAP_memchr
132 WRAPPER2(void *, memchr, const void *s, int c, size_t n)
133 {
134   TRACE ("%s\n", __PRETTY_FUNCTION__);
135   MF_VALIDATE_EXTENT(s, n, __MF_CHECK_READ, "memchr region");
136   return memchr (s, c, n);
137 }
138 #endif
139
140 #ifdef WRAP_memrchr
141 WRAPPER2(void *, memrchr, const void *s, int c, size_t n)
142 {
143   TRACE ("%s\n", __PRETTY_FUNCTION__);
144   MF_VALIDATE_EXTENT(s, n, __MF_CHECK_READ, "memrchr region");
145   return memrchr (s, c, n);
146 }
147 #endif
148
149 #ifdef WRAP_strcpy
150 WRAPPER2(char *, strcpy, char *dest, const char *src)
151 {
152   /* nb: just because strlen(src) == n doesn't mean (src + n) or (src + n +
153      1) are valid pointers. the allocated object might have size < n.
154      check anyways. */
155
156   size_t n = strlen (src);
157   TRACE ("%s\n", __PRETTY_FUNCTION__);
158   MF_VALIDATE_EXTENT(src, CLAMPADD(n, 1), __MF_CHECK_READ, "strcpy src"); 
159   MF_VALIDATE_EXTENT(dest, CLAMPADD(n, 1), __MF_CHECK_WRITE, "strcpy dest");
160   return strcpy (dest, src);
161 }
162 #endif
163
164 #ifdef WRAP_strncpy
165 WRAPPER2(char *, strncpy, char *dest, const char *src, size_t n)
166 {
167   size_t len = strnlen (src, n);
168   TRACE ("%s\n", __PRETTY_FUNCTION__);
169   MF_VALIDATE_EXTENT(src, len, __MF_CHECK_READ, "strncpy src");
170   MF_VALIDATE_EXTENT(dest, len, __MF_CHECK_WRITE, "strncpy dest"); /* nb: strNcpy */
171   return strncpy (dest, src, n);
172 }
173 #endif
174
175 #ifdef WRAP_strcat
176 WRAPPER2(char *, strcat, char *dest, const char *src)
177 {
178   size_t dest_sz;
179   size_t src_sz;
180   TRACE ("%s\n", __PRETTY_FUNCTION__);
181   dest_sz = strlen (dest);
182   src_sz = strlen (src);  
183   MF_VALIDATE_EXTENT(src, CLAMPADD(src_sz, 1), __MF_CHECK_READ, "strcat src");
184   MF_VALIDATE_EXTENT(dest, CLAMPADD(dest_sz, CLAMPADD(src_sz, 1)),
185                      __MF_CHECK_WRITE, "strcat dest");
186   return strcat (dest, src);
187 }
188 #endif
189
190 #ifdef WRAP_strncat
191 WRAPPER2(char *, strncat, char *dest, const char *src, size_t n)
192 {
193
194   /* nb: validating the extents (s,n) might be a mistake for two reasons.
195      
196   (1) the string s might be shorter than n chars, and n is just a 
197   poor choice by the programmer. this is not a "true" error in the
198   sense that the call to strncat would still be ok.
199   
200   (2) we could try to compensate for case (1) by calling strlen(s) and
201   using that as a bound for the extent to verify, but strlen might fall off
202   the end of a non-terminated string, leading to a false positive.
203   
204   so we will call strnlen(s,n) and use that as a bound.
205
206   if strnlen returns a length beyond the end of the registered extent
207   associated with s, there is an error: the programmer's estimate for n is
208   too large _AND_ the string s is unterminated, in which case they'd be
209   about to touch memory they don't own while calling strncat.
210
211   this same logic applies to further uses of strnlen later down in this
212   file. */
213
214   size_t src_sz;
215   size_t dest_sz;
216   TRACE ("%s\n", __PRETTY_FUNCTION__);
217   src_sz = strnlen (src, n);
218   dest_sz = strnlen (dest, n);
219   MF_VALIDATE_EXTENT(src, src_sz, __MF_CHECK_READ, "strncat src");
220   MF_VALIDATE_EXTENT(dest, (CLAMPADD(dest_sz, CLAMPADD(src_sz, 1))),
221                      __MF_CHECK_WRITE, "strncat dest");
222   return strncat (dest, src, n);
223 }
224 #endif
225
226 #ifdef WRAP_strcmp
227 WRAPPER2(int, strcmp, const char *s1, const char *s2)
228 {
229   size_t s1_sz;
230   size_t s2_sz;
231   TRACE ("%s\n", __PRETTY_FUNCTION__);
232   s1_sz = strlen (s1);
233   s2_sz = strlen (s2);  
234   MF_VALIDATE_EXTENT(s1, CLAMPADD(s1_sz, 1), __MF_CHECK_READ, "strcmp 1st arg");
235   MF_VALIDATE_EXTENT(s2, CLAMPADD(s2_sz, 1), __MF_CHECK_WRITE, "strcmp 2nd arg");
236   return strcmp (s1, s2);
237 }
238 #endif
239
240 #ifdef WRAP_strcasecmp
241 WRAPPER2(int, strcasecmp, const char *s1, const char *s2)
242 {
243   size_t s1_sz;
244   size_t s2_sz;
245   TRACE ("%s\n", __PRETTY_FUNCTION__);
246   s1_sz = strlen (s1);
247   s2_sz = strlen (s2);  
248   MF_VALIDATE_EXTENT(s1, CLAMPADD(s1_sz, 1), __MF_CHECK_READ, "strcasecmp 1st arg");
249   MF_VALIDATE_EXTENT(s2, CLAMPADD(s2_sz, 1), __MF_CHECK_READ, "strcasecmp 2nd arg");
250   return strcasecmp (s1, s2);
251 }
252 #endif
253
254 #ifdef WRAP_strncmp
255 WRAPPER2(int, strncmp, const char *s1, const char *s2, size_t n)
256 {
257   size_t s1_sz;
258   size_t s2_sz;
259   TRACE ("%s\n", __PRETTY_FUNCTION__);
260   s1_sz = strnlen (s1, n);
261   s2_sz = strnlen (s2, n);
262   MF_VALIDATE_EXTENT(s1, s1_sz, __MF_CHECK_READ, "strncmp 1st arg");
263   MF_VALIDATE_EXTENT(s2, s2_sz, __MF_CHECK_READ, "strncmp 2nd arg");
264   return strncmp (s1, s2, n);
265 }
266 #endif
267
268 #ifdef WRAP_strncasecmp
269 WRAPPER2(int, strncasecmp, const char *s1, const char *s2, size_t n)
270 {
271   size_t s1_sz;
272   size_t s2_sz;
273   TRACE ("%s\n", __PRETTY_FUNCTION__);
274   s1_sz = strnlen (s1, n);
275   s2_sz = strnlen (s2, n);
276   MF_VALIDATE_EXTENT(s1, s1_sz, __MF_CHECK_READ, "strncasecmp 1st arg");
277   MF_VALIDATE_EXTENT(s2, s2_sz, __MF_CHECK_READ, "strncasecmp 2nd arg");
278   return strncasecmp (s1, s2, n);
279 }
280 #endif
281
282 #ifdef WRAP_strdup
283 WRAPPER2(char *, strdup, const char *s)
284 {
285   DECLARE(void *, malloc, size_t sz);
286   char *result;
287   size_t n = strlen (s);
288   TRACE ("%s\n", __PRETTY_FUNCTION__);
289   MF_VALIDATE_EXTENT(s, CLAMPADD(n,1), __MF_CHECK_READ, "strdup region");
290   result = (char *)CALL_REAL(malloc, 
291                              CLAMPADD(CLAMPADD(n,1),
292                                       CLAMPADD(__mf_opts.crumple_zone,
293                                                __mf_opts.crumple_zone)));
294
295   if (UNLIKELY(! result)) return result;
296
297   result += __mf_opts.crumple_zone;
298   memcpy (result, s, n);
299   result[n] = '\0';
300
301   __mf_register (result, CLAMPADD(n,1), __MF_TYPE_HEAP_I, "strdup region");
302   return result;
303 }
304 #endif
305
306 #ifdef WRAP_strndup
307 WRAPPER2(char *, strndup, const char *s, size_t n)
308 {
309   DECLARE(void *, malloc, size_t sz);
310   char *result;
311   size_t sz = strnlen (s, n);
312   TRACE ("%s\n", __PRETTY_FUNCTION__);
313   MF_VALIDATE_EXTENT(s, sz, __MF_CHECK_READ, "strndup region"); /* nb: strNdup */
314
315   /* note: strndup still adds a \0, even with the N limit! */
316   result = (char *)CALL_REAL(malloc, 
317                              CLAMPADD(CLAMPADD(n,1),
318                                       CLAMPADD(__mf_opts.crumple_zone,
319                                                __mf_opts.crumple_zone)));
320   
321   if (UNLIKELY(! result)) return result;
322
323   result += __mf_opts.crumple_zone;
324   memcpy (result, s, n);
325   result[n] = '\0';
326
327   __mf_register (result, CLAMPADD(n,1), __MF_TYPE_HEAP_I, "strndup region");
328   return result;
329 }
330 #endif
331
332 #ifdef WRAP_strchr
333 WRAPPER2(char *, strchr, const char *s, int c)
334 {
335   size_t n;
336   TRACE ("%s\n", __PRETTY_FUNCTION__);
337   n = strlen (s);
338   MF_VALIDATE_EXTENT(s, CLAMPADD(n,1), __MF_CHECK_READ, "strchr region");
339   return strchr (s, c);
340 }
341 #endif
342
343 #ifdef WRAP_strrchr
344 WRAPPER2(char *, strrchr, const char *s, int c)
345 {
346   size_t n;
347   TRACE ("%s\n", __PRETTY_FUNCTION__);
348   n = strlen (s);
349   MF_VALIDATE_EXTENT(s, CLAMPADD(n,1), __MF_CHECK_READ, "strrchr region");
350   return strrchr (s, c);
351 }
352 #endif
353
354 #ifdef WRAP_strstr
355 WRAPPER2(char *, strstr, const char *haystack, const char *needle)
356 {
357   size_t haystack_sz;
358   size_t needle_sz;
359   TRACE ("%s\n", __PRETTY_FUNCTION__);
360   haystack_sz = strlen (haystack);
361   needle_sz = strlen (needle);
362   MF_VALIDATE_EXTENT(haystack, CLAMPADD(haystack_sz, 1), __MF_CHECK_READ, "strstr haystack");
363   MF_VALIDATE_EXTENT(needle, CLAMPADD(needle_sz, 1), __MF_CHECK_READ, "strstr needle");
364   return strstr (haystack, needle);
365 }
366 #endif
367
368 #ifdef WRAP_memmem
369 WRAPPER2(void *, memmem, 
370         const void *haystack, size_t haystacklen,
371         const void *needle, size_t needlelen)
372 {
373   TRACE ("%s\n", __PRETTY_FUNCTION__);
374   MF_VALIDATE_EXTENT(haystack, haystacklen, __MF_CHECK_READ, "memmem haystack");
375   MF_VALIDATE_EXTENT(needle, needlelen, __MF_CHECK_READ, "memmem needle");
376   return memmem (haystack, haystacklen, needle, needlelen);
377 }
378 #endif
379
380 #ifdef WRAP_strlen
381 WRAPPER2(size_t, strlen, const char *s)
382 {
383   size_t result = strlen (s);
384   TRACE ("%s\n", __PRETTY_FUNCTION__);
385   MF_VALIDATE_EXTENT(s, CLAMPADD(result, 1), __MF_CHECK_READ, "strlen region");
386   return result;
387 }
388 #endif
389
390 #ifdef WRAP_strnlen
391 WRAPPER2(size_t, strnlen, const char *s, size_t n)
392 {
393   size_t result = strnlen (s, n);
394   TRACE ("%s\n", __PRETTY_FUNCTION__);
395   MF_VALIDATE_EXTENT(s, result, __MF_CHECK_READ, "strnlen region");
396   return result;
397 }
398 #endif
399
400 #ifdef WRAP_bzero
401 WRAPPER2(void, bzero, void *s, size_t n)
402 {
403   TRACE ("%s\n", __PRETTY_FUNCTION__);
404   MF_VALIDATE_EXTENT(s, n, __MF_CHECK_WRITE, "bzero region");
405   bzero (s, n);
406 }
407 #endif
408
409 #ifdef WRAP_bcopy
410 #undef bcopy
411 WRAPPER2(void, bcopy, const void *src, void *dest, size_t n)
412 {
413   TRACE ("%s\n", __PRETTY_FUNCTION__);
414   MF_VALIDATE_EXTENT(src, n, __MF_CHECK_READ, "bcopy src");
415   MF_VALIDATE_EXTENT(dest, n, __MF_CHECK_WRITE, "bcopy dest");
416   bcopy (src, dest, n);
417 }
418 #endif
419
420 #ifdef WRAP_bcmp
421 #undef bcmp
422 WRAPPER2(int, bcmp, const void *s1, const void *s2, size_t n)
423 {
424   TRACE ("%s\n", __PRETTY_FUNCTION__);
425   MF_VALIDATE_EXTENT(s1, n, __MF_CHECK_READ, "bcmp 1st arg");
426   MF_VALIDATE_EXTENT(s2, n, __MF_CHECK_READ, "bcmp 2nd arg");
427   return bcmp (s1, s2, n);
428 }
429 #endif
430
431 #ifdef WRAP_index
432 WRAPPER2(char *, index, const char *s, int c)
433 {
434   size_t n = strlen (s);
435   TRACE ("%s\n", __PRETTY_FUNCTION__);
436   MF_VALIDATE_EXTENT(s, CLAMPADD(n, 1), __MF_CHECK_READ, "index region");
437   return index (s, c);
438 }
439 #endif
440
441 #ifdef WRAP_rindex
442 WRAPPER2(char *, rindex, const char *s, int c)
443 {
444   size_t n = strlen (s);
445   TRACE ("%s\n", __PRETTY_FUNCTION__);
446   MF_VALIDATE_EXTENT(s, CLAMPADD(n, 1), __MF_CHECK_READ, "rindex region");
447   return rindex (s, c);
448 }
449 #endif
450
451 /* XXX:  stpcpy, memccpy */
452
453
454 /* XXX: *printf,*scanf */
455
456
457 /* XXX: setjmp, longjmp */
458
459 #ifdef WRAP_asctime
460 WRAPPER2(char *, asctime, struct tm *tm)
461 {
462   static char *reg_result = NULL;
463   char *result;
464   TRACE ("%s\n", __PRETTY_FUNCTION__);
465   MF_VALIDATE_EXTENT(tm, sizeof (struct tm), __MF_CHECK_READ, "asctime tm");
466   result = asctime (tm);
467   if (reg_result == NULL)
468     {
469       __mf_register (result, strlen (result)+1, __MF_TYPE_STATIC, "asctime string");
470       reg_result = result;
471     }
472   return result;
473 }
474 #endif
475
476 #ifdef WRAP_ctime
477 WRAPPER2(char *, ctime, const time_t *timep)
478 {
479   static char *reg_result = NULL;
480   char *result;
481   TRACE ("%s\n", __PRETTY_FUNCTION__);
482   MF_VALIDATE_EXTENT(timep, sizeof (time_t), __MF_CHECK_READ, "ctime time");
483   result = ctime (timep);
484   if (reg_result == NULL)
485     {
486       /* XXX: what if asctime and ctime return the same static ptr? */
487       __mf_register (result, strlen (result)+1, __MF_TYPE_STATIC, "ctime string");
488       reg_result = result;
489     }
490   return result;
491 }
492 #endif
493
494
495 #ifdef WRAP_localtime
496 WRAPPER2(struct tm*, localtime, const time_t *timep)
497 {
498   static struct tm *reg_result = NULL;
499   struct tm *result;
500   TRACE ("%s\n", __PRETTY_FUNCTION__);
501   MF_VALIDATE_EXTENT(timep, sizeof (time_t), __MF_CHECK_READ, "localtime time");
502   result = localtime (timep);
503   if (reg_result == NULL)
504     {
505       __mf_register (result, sizeof (struct tm), __MF_TYPE_STATIC, "localtime tm");
506       reg_result = result;
507     }
508   return result;
509 }
510 #endif
511
512 #ifdef WRAP_gmtime
513 WRAPPER2(struct tm*, gmtime, const time_t *timep)
514 {
515   static struct tm *reg_result = NULL;
516   struct tm *result;
517   TRACE ("%s\n", __PRETTY_FUNCTION__);
518   MF_VALIDATE_EXTENT(timep, sizeof (time_t), __MF_CHECK_READ, "gmtime time");
519   result = gmtime (timep);
520   if (reg_result == NULL)
521     {
522       __mf_register (result, sizeof (struct tm), __MF_TYPE_STATIC, "gmtime tm");
523       reg_result = result;
524     }
525   return result;
526 }
527 #endif
528
529
530
531 /* EL start */
532
533 /* The following indicate if the result of the corresponding function
534  * should be explicitly un/registered by the wrapper
535 */
536 #define MF_REGISTER_strerror            __MF_TYPE_STATIC
537 #undef  MF_REGISTER_fopen
538 #define MF_RESULT_SIZE_fopen            (sizeof (FILE))
539 #undef  MF_REGISTER_opendir
540 #define MF_RESULT_SIZE_opendir          0       /* (sizeof (DIR)) */
541 #undef  MF_REGISTER_readdir
542 #define MF_REGISTER_gethostbyname       __MF_TYPE_STATIC
543 #undef  MF_REGISTER_gethostbyname_items
544 #undef  MF_REGISTER_dlopen
545 #undef  MF_REGISTER_dlerror
546 #undef  MF_REGISTER_dlsym
547 #define MF_REGISTER_shmat               __MF_TYPE_GUESS
548
549
550 #ifdef WRAP_time
551 #include <time.h>
552 WRAPPER2(time_t, time, time_t *timep)
553 {
554   TRACE ("%s\n", __PRETTY_FUNCTION__);
555   if (NULL != timep)
556     MF_VALIDATE_EXTENT (timep, sizeof (*timep), __MF_CHECK_WRITE,
557       "time timep");
558   return time (timep);
559 }
560 #endif
561
562 #ifdef WRAP_strerror
563 WRAPPER2(char *, strerror, int errnum)
564 {
565   char *p;
566   size_t n;
567   TRACE ("%s\n", __PRETTY_FUNCTION__);
568   p = strerror (errnum);
569   if (NULL != p) {
570     n = strlen (p);
571     n = CLAMPADD(n, 1);
572 #ifdef MF_REGISTER_strerror
573     __mf_register (p, n, MF_REGISTER_strerror, "strerror result");
574 #endif
575     MF_VALIDATE_EXTENT (p, n, __MF_CHECK_WRITE, "strerror result");
576   }
577   return p;
578 }
579 #endif
580
581 #ifdef WRAP_fopen
582 WRAPPER2(FILE *, fopen, const char *path, const char *mode)
583 {
584   size_t n;
585   FILE *p;
586   TRACE ("%s\n", __PRETTY_FUNCTION__);
587
588   n = strlen (path);
589   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "fopen path");
590
591   n = strlen (mode);
592   MF_VALIDATE_EXTENT (mode, CLAMPADD(n, 1), __MF_CHECK_READ, "fopen mode");
593
594   p = fopen (path, mode);
595   if (NULL != p) {
596 #ifdef MF_REGISTER_fopen
597     __mf_register (p, sizeof (*p), MF_REGISTER_fopen, "fopen result");
598 #endif
599     MF_VALIDATE_EXTENT (p, sizeof (*p), __MF_CHECK_WRITE, "fopen result");
600   }
601
602   return p;
603 }
604 #endif
605
606 #ifdef HAVE_FOPEN64
607 #ifdef WRAP_fopen64
608 WRAPPER2(FILE *, fopen64, const char *path, const char *mode)
609 {
610   size_t n;
611   FILE *p;
612   TRACE ("%s\n", __PRETTY_FUNCTION__);
613
614   n = strlen (path);
615   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "fopen64 path");
616
617   n = strlen (mode);
618   MF_VALIDATE_EXTENT (mode, CLAMPADD(n, 1), __MF_CHECK_READ, "fopen64 mode");
619
620   p = fopen64 (path, mode);
621   if (NULL != p) {
622 #ifdef MF_REGISTER_fopen
623     __mf_register (p, sizeof (*p), MF_REGISTER_fopen, "fopen64 result");
624 #endif
625     MF_VALIDATE_EXTENT (p, sizeof (*p), __MF_CHECK_WRITE, "fopen64 result");
626   }
627
628   return p;
629 }
630 #endif
631 #endif
632
633 #ifdef WRAP_fclose
634 WRAPPER2(int, fclose, FILE *stream)
635 {
636   int resp;
637   TRACE ("%s\n", __PRETTY_FUNCTION__);
638   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
639     "fclose stream");
640   resp = fclose (stream);
641 #ifdef MF_REGISTER_fopen
642   __mf_unregister (stream, sizeof (*stream));
643 #endif
644
645   return resp;
646 }
647 #endif
648
649 #ifdef WRAP_fread
650 WRAPPER2(size_t, fread, void *ptr, size_t size, size_t nmemb, FILE *stream)
651 {
652   TRACE ("%s\n", __PRETTY_FUNCTION__);
653   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
654     "fread stream");
655   MF_VALIDATE_EXTENT (ptr, size * nmemb, __MF_CHECK_WRITE, "fread buffer");
656   return fread (ptr, size, nmemb, stream);
657 }
658 #endif
659
660 #ifdef WRAP_fwrite
661 WRAPPER2(size_t, fwrite, const void *ptr, size_t size, size_t nmemb,
662         FILE *stream)
663 {
664   TRACE ("%s\n", __PRETTY_FUNCTION__);
665   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
666     "fwrite stream");
667   MF_VALIDATE_EXTENT (ptr, size * nmemb, __MF_CHECK_READ, "fwrite buffer");
668   return fwrite (ptr, size, nmemb, stream);
669 }
670 #endif
671
672 #ifdef WRAP_fgetc
673 WRAPPER2(int, fgetc, FILE *stream)
674 {
675   TRACE ("%s\n", __PRETTY_FUNCTION__);
676   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
677     "fgetc stream");
678   return fgetc (stream);
679 }
680 #endif
681
682 #ifdef WRAP_fgets
683 WRAPPER2(char *, fgets, char *s, int size, FILE *stream)
684 {
685   TRACE ("%s\n", __PRETTY_FUNCTION__);
686   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
687     "fgets stream");
688   MF_VALIDATE_EXTENT (s, size, __MF_CHECK_WRITE, "fgets buffer");
689   return fgets (s, size, stream);
690 }
691 #endif
692
693 #ifdef WRAP_getc
694 WRAPPER2(int, getc, FILE *stream)
695 {
696   TRACE ("%s\n", __PRETTY_FUNCTION__);
697   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
698     "getc stream");
699   return getc (stream);
700 }
701 #endif
702
703 #ifdef WRAP_gets
704 WRAPPER2(char *, gets, char *s)
705 {
706   TRACE ("%s\n", __PRETTY_FUNCTION__);
707   MF_VALIDATE_EXTENT (s, 1, __MF_CHECK_WRITE, "gets buffer");
708   /* Avoid link-time warning... */
709   s = fgets (s, INT_MAX, stdin);
710   if (NULL != s) {      /* better late than never */
711     size_t n = strlen (s);
712     MF_VALIDATE_EXTENT (s, CLAMPADD(n, 1), __MF_CHECK_WRITE, "gets buffer");
713   }
714   return s;
715 }
716 #endif
717
718 #ifdef WRAP_ungetc
719 WRAPPER2(int, ungetc, int c, FILE *stream)
720 {
721   TRACE ("%s\n", __PRETTY_FUNCTION__);
722   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
723      "ungetc stream");
724   return ungetc (c, stream);
725 }
726 #endif
727
728 #ifdef WRAP_fputc
729 WRAPPER2(int, fputc, int c, FILE *stream)
730 {
731   TRACE ("%s\n", __PRETTY_FUNCTION__);
732   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
733     "fputc stream");
734   return fputc (c, stream);
735 }
736 #endif
737
738 #ifdef WRAP_fputs
739 WRAPPER2(int, fputs, const char *s, FILE *stream)
740 {
741   size_t n;
742   TRACE ("%s\n", __PRETTY_FUNCTION__);
743   n = strlen (s);
744   MF_VALIDATE_EXTENT (s, CLAMPADD(n, 1), __MF_CHECK_READ, "fputs buffer");
745   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
746     "fputs stream");
747   return fputs (s, stream);
748 }
749 #endif
750
751 #ifdef WRAP_putc
752 WRAPPER2(int, putc, int c, FILE *stream)
753 {
754   TRACE ("%s\n", __PRETTY_FUNCTION__);
755   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
756     "putc stream");
757   return putc (c, stream);
758 }
759 #endif
760
761 #ifdef WRAP_puts
762 WRAPPER2(int, puts, const char *s)
763 {
764   size_t n;
765   TRACE ("%s\n", __PRETTY_FUNCTION__);
766   n = strlen (s);
767   MF_VALIDATE_EXTENT (s, CLAMPADD(n, 1), __MF_CHECK_READ, "puts buffer");
768   return puts (s);
769 }
770 #endif
771
772 #ifdef WRAP_clearerr
773 WRAPPER2(void, clearerr, FILE *stream)
774 {
775   TRACE ("%s\n", __PRETTY_FUNCTION__);
776   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
777     "clearerr stream");
778   clearerr (stream);
779 }
780 #endif
781
782 #ifdef WRAP_feof
783 WRAPPER2(int, feof, FILE *stream)
784 {
785   TRACE ("%s\n", __PRETTY_FUNCTION__);
786   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
787     "feof stream");
788   return feof (stream);
789 }
790 #endif
791
792 #ifdef WRAP_ferror
793 WRAPPER2(int, ferror, FILE *stream)
794 {
795   TRACE ("%s\n", __PRETTY_FUNCTION__);
796   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
797     "ferror stream");
798   return ferror (stream);
799 }
800 #endif
801
802 #ifdef WRAP_fileno
803 #include <stdio.h>
804 WRAPPER2(int, fileno, FILE *stream)
805 {
806   TRACE ("%s\n", __PRETTY_FUNCTION__);
807   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
808     "fileno stream");
809   return fileno (stream);
810 }
811 #endif
812
813 #ifdef WRAP_printf
814 #include <stdio.h>
815 #include <stdarg.h>
816 WRAPPER2(int, printf, const char *format, ...)
817 {
818   size_t n;
819   va_list ap;
820   int result;
821   TRACE ("%s\n", __PRETTY_FUNCTION__);
822   n = strlen (format);
823   MF_VALIDATE_EXTENT (format, CLAMPADD(n, 1), __MF_CHECK_READ,
824     "printf format");
825   va_start (ap, format);
826   result = vprintf (format, ap);
827   va_end (ap);
828   return result;
829 }
830 #endif
831
832 #ifdef WRAP_fprintf
833 #include <stdio.h>
834 #include <stdarg.h>
835 WRAPPER2(int, fprintf, FILE *stream, const char *format, ...)
836 {
837   size_t n;
838   va_list ap;
839   int result;
840   TRACE ("%s\n", __PRETTY_FUNCTION__);
841   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
842     "fprintf stream");
843   n = strlen (format);
844   MF_VALIDATE_EXTENT (format, CLAMPADD(n, 1), __MF_CHECK_READ,
845     "fprintf format");
846   va_start (ap, format);
847   result = vfprintf (stream, format, ap);
848   va_end (ap);
849   return result;
850 }
851 #endif
852
853 #ifdef WRAP_sprintf
854 #include <stdio.h>
855 #include <stdarg.h>
856 WRAPPER2(int, sprintf, char *str, const char *format, ...)
857 {
858   size_t n;
859   va_list ap;
860   int result;
861   TRACE ("%s\n", __PRETTY_FUNCTION__);
862   MF_VALIDATE_EXTENT (str, 1, __MF_CHECK_WRITE, "sprintf str");
863   n = strlen (format);
864   MF_VALIDATE_EXTENT (format, CLAMPADD(n, 1), __MF_CHECK_READ,
865     "sprintf format");
866   va_start (ap, format);
867   result = vsprintf (str, format, ap);
868   va_end (ap);
869   n = strlen (str);
870   MF_VALIDATE_EXTENT (str, CLAMPADD(n, 1), __MF_CHECK_WRITE, "sprintf str");
871   return result;
872 }
873 #endif
874
875 #ifdef WRAP_snprintf
876 #include <stdio.h>
877 #include <stdarg.h>
878 WRAPPER2(int, snprintf, char *str, size_t size, const char *format, ...)
879 {
880   size_t n;
881   va_list ap;
882   int result;
883   TRACE ("%s\n", __PRETTY_FUNCTION__);
884   MF_VALIDATE_EXTENT (str, size, __MF_CHECK_WRITE, "snprintf str");
885   n = strlen (format);
886   MF_VALIDATE_EXTENT (format, CLAMPADD(n, 1), __MF_CHECK_READ,
887     "snprintf format");
888   va_start (ap, format);
889   result = vsnprintf (str, size, format, ap);
890   va_end (ap);
891   return result;
892 }
893 #endif
894
895 #ifdef WRAP_vprintf
896 #include <stdio.h>
897 #include <stdarg.h>
898 WRAPPER2(int, vprintf,  const char *format, va_list ap)
899 {
900   size_t n;
901   TRACE ("%s\n", __PRETTY_FUNCTION__);
902   n = strlen (format);
903   MF_VALIDATE_EXTENT (format, CLAMPADD(n, 1), __MF_CHECK_READ,
904     "vprintf format");
905   return vprintf (format, ap);
906 }
907 #endif
908
909 #ifdef WRAP_vfprintf
910 #include <stdio.h>
911 #include <stdarg.h>
912 WRAPPER2(int, vfprintf, FILE *stream, const char *format, va_list ap)
913 {
914   size_t n;
915   TRACE ("%s\n", __PRETTY_FUNCTION__);
916   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
917     "vfprintf stream");
918   n = strlen (format);
919   MF_VALIDATE_EXTENT (format, CLAMPADD(n, 1), __MF_CHECK_READ,
920     "vfprintf format");
921   return vfprintf (stream, format, ap);
922 }
923 #endif
924
925 #ifdef WRAP_vsprintf
926 #include <stdio.h>
927 #include <stdarg.h>
928 WRAPPER2(int, vsprintf, char *str, const char *format, va_list ap)
929 {
930   size_t n;
931   int result;
932   TRACE ("%s\n", __PRETTY_FUNCTION__);
933   MF_VALIDATE_EXTENT (str, 1, __MF_CHECK_WRITE, "vsprintf str");
934   n = strlen (format);
935   MF_VALIDATE_EXTENT (format, CLAMPADD(n, 1), __MF_CHECK_READ,
936     "vsprintf format");
937   result = vsprintf (str, format, ap);
938   n = strlen (str);
939   MF_VALIDATE_EXTENT (str, CLAMPADD(n, 1), __MF_CHECK_WRITE, "vsprintf str");
940   return result;
941 }
942 #endif
943
944 #ifdef WRAP_vsnprintf
945 #include <stdio.h>
946 #include <stdarg.h>
947 WRAPPER2(int, vsnprintf, char *str, size_t size, const char *format,
948         va_list ap)
949 {
950   size_t n;
951   TRACE ("%s\n", __PRETTY_FUNCTION__);
952   MF_VALIDATE_EXTENT (str, size, __MF_CHECK_WRITE, "vsnprintf str");
953   n = strlen (format);
954   MF_VALIDATE_EXTENT (format, CLAMPADD(n, 1), __MF_CHECK_READ,
955     "vsnprintf format");
956   return vsnprintf (str, size, format, ap);
957 }
958 #endif
959
960 #ifdef WRAP_access
961 WRAPPER2(int , access, const char *path, int mode)
962 {
963   size_t n;
964   TRACE ("%s\n", __PRETTY_FUNCTION__);
965   n = strlen (path);
966   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "access path");
967   return access (path, mode);
968 }
969 #endif
970
971 #ifdef WRAP_remove
972 WRAPPER2(int , remove, const char *path)
973 {
974   size_t n;
975   TRACE ("%s\n", __PRETTY_FUNCTION__);
976   n = strlen (path);
977   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "remove path");
978   return remove (path);
979 }
980 #endif
981
982 #ifdef WRAP_fflush
983 WRAPPER2(int, fflush, FILE *stream)
984 {
985   TRACE ("%s\n", __PRETTY_FUNCTION__);
986   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
987     "fflush stream");
988   return fflush (stream);
989 }
990 #endif
991
992 #ifdef WRAP_fseek
993 WRAPPER2(int, fseek, FILE *stream, long offset, int whence)
994 {
995   TRACE ("%s\n", __PRETTY_FUNCTION__);
996   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
997     "fseek stream");
998   return fseek (stream, offset, whence);
999 }
1000 #endif
1001
1002 #ifdef HAVE_FSEEKO64
1003 #ifdef WRAP_fseeko64
1004 WRAPPER2(int, fseeko64, FILE *stream, off64_t offset, int whence)
1005 {
1006   TRACE ("%s\n", __PRETTY_FUNCTION__);
1007   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
1008     "fseeko64 stream");
1009   return fseeko64 (stream, offset, whence);
1010 }
1011 #endif
1012 #endif
1013
1014 #ifdef WRAP_ftell
1015 WRAPPER2(long, ftell, FILE *stream)
1016 {
1017   TRACE ("%s\n", __PRETTY_FUNCTION__);
1018   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
1019     "ftell stream");
1020   return ftell (stream);
1021 }
1022 #endif
1023
1024 #ifdef HAVE_FTELLO64
1025 #ifdef WRAP_ftello64
1026 WRAPPER2(off64_t, ftello64, FILE *stream)
1027 {
1028   TRACE ("%s\n", __PRETTY_FUNCTION__);
1029   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
1030     "ftello64 stream");
1031   return ftello64 (stream);
1032 }
1033 #endif
1034 #endif
1035
1036 #ifdef WRAP_rewind
1037 WRAPPER2(void, rewind, FILE *stream)
1038 {
1039   TRACE ("%s\n", __PRETTY_FUNCTION__);
1040   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
1041     "rewind stream");
1042   rewind (stream);
1043 }
1044 #endif
1045
1046 #ifdef WRAP_fgetpos
1047 WRAPPER2(int, fgetpos, FILE *stream, fpos_t *pos)
1048 {
1049   TRACE ("%s\n", __PRETTY_FUNCTION__);
1050   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
1051     "fgetpos stream");
1052   MF_VALIDATE_EXTENT (pos, sizeof (*pos), __MF_CHECK_WRITE, "fgetpos pos");
1053   return fgetpos (stream, pos);
1054 }
1055 #endif
1056
1057 #ifdef WRAP_fsetpos
1058 WRAPPER2(int, fsetpos, FILE *stream, fpos_t *pos)
1059 {
1060   TRACE ("%s\n", __PRETTY_FUNCTION__);
1061   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
1062     "fsetpos stream");
1063   MF_VALIDATE_EXTENT (pos, sizeof (*pos), __MF_CHECK_READ, "fsetpos pos");
1064   return fsetpos (stream, pos);
1065 }
1066 #endif
1067
1068 #ifdef WRAP_stat
1069 #include <sys/stat.h>
1070 WRAPPER2(int , stat, const char *path, struct stat *buf)
1071 {
1072   size_t n;
1073   TRACE ("%s\n", __PRETTY_FUNCTION__);
1074   n = strlen (path);
1075   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "stat path");
1076   MF_VALIDATE_EXTENT (buf, sizeof (*buf), __MF_CHECK_READ, "stat buf");
1077   return stat (path, buf);
1078 }
1079 #endif
1080
1081 #ifdef HAVE_STAT64
1082 #ifdef WRAP_stat64
1083 #include <sys/stat.h>
1084 WRAPPER2(int , stat64, const char *path, struct stat64 *buf)
1085 {
1086   size_t n;
1087   TRACE ("%s\n", __PRETTY_FUNCTION__);
1088   n = strlen (path);
1089   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "stat64 path");
1090   MF_VALIDATE_EXTENT (buf, sizeof (*buf), __MF_CHECK_READ, "stat64 buf");
1091   return stat64 (path, buf);
1092 }
1093 #endif
1094 #endif
1095
1096 #ifdef WRAP_fstat
1097 #include <sys/stat.h>
1098 WRAPPER2(int , fstat, int filedes, struct stat *buf)
1099 {
1100   TRACE ("%s\n", __PRETTY_FUNCTION__);
1101   MF_VALIDATE_EXTENT (buf, sizeof (*buf), __MF_CHECK_READ, "fstat buf");
1102   return fstat (filedes, buf);
1103 }
1104 #endif
1105
1106 #ifdef WRAP_lstat
1107 #include <sys/stat.h>
1108 WRAPPER2(int , lstat, const char *path, struct stat *buf)
1109 {
1110   size_t n;
1111   TRACE ("%s\n", __PRETTY_FUNCTION__);
1112   n = strlen (path);
1113   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "lstat path");
1114   MF_VALIDATE_EXTENT (buf, sizeof (*buf), __MF_CHECK_READ, "lstat buf");
1115   return lstat (path, buf);
1116 }
1117 #endif
1118
1119 #ifdef WRAP_mkfifo
1120 #include <sys/stat.h>
1121 WRAPPER2(int , mkfifo, const char *path, mode_t mode)
1122 {
1123   size_t n;
1124   TRACE ("%s\n", __PRETTY_FUNCTION__);
1125   n = strlen (path);
1126   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "mkfifo path");
1127   return mkfifo (path, mode);
1128 }
1129 #endif
1130
1131 #ifdef WRAP_setvbuf
1132 WRAPPER2(int, setvbuf, FILE *stream, char *buf, int mode , size_t size)
1133 {
1134   TRACE ("%s\n", __PRETTY_FUNCTION__);
1135   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
1136     "setvbuf stream");
1137   if (NULL != buf)
1138     MF_VALIDATE_EXTENT (buf, size, __MF_CHECK_READ, "setvbuf buf");
1139   return setvbuf (stream, buf, mode, size);
1140 }
1141 #endif
1142
1143 #ifdef WRAP_setbuf
1144 WRAPPER2(void, setbuf, FILE *stream, char *buf)
1145 {
1146   TRACE ("%s\n", __PRETTY_FUNCTION__);
1147   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
1148     "setbuf stream");
1149   if (NULL != buf)
1150     MF_VALIDATE_EXTENT (buf, BUFSIZ, __MF_CHECK_READ, "setbuf buf");
1151   setbuf (stream, buf);
1152 }
1153 #endif
1154
1155 #ifdef WRAP_opendir
1156 #include <dirent.h>
1157 WRAPPER2(DIR *, opendir, const char *path)
1158 {
1159   DIR *p;
1160   size_t n;
1161   TRACE ("%s\n", __PRETTY_FUNCTION__);
1162   n = strlen (path);
1163   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "opendir path");
1164
1165   p = opendir (path);
1166   if (NULL != p) {
1167 #ifdef MF_REGISTER_opendir
1168     __mf_register (p, MF_RESULT_SIZE_opendir, MF_REGISTER_opendir,
1169       "opendir result");
1170 #endif
1171     MF_VALIDATE_EXTENT (p, MF_RESULT_SIZE_opendir, __MF_CHECK_WRITE,
1172       "opendir result");
1173   }
1174   return p;
1175 }
1176 #endif
1177
1178 #ifdef WRAP_closedir
1179 #include <dirent.h>
1180 WRAPPER2(int, closedir, DIR *dir)
1181 {
1182   TRACE ("%s\n", __PRETTY_FUNCTION__);
1183   MF_VALIDATE_EXTENT (dir, 0, __MF_CHECK_WRITE, "closedir dir");
1184 #ifdef MF_REGISTER_opendir
1185   __mf_unregister (dir, MF_RESULT_SIZE_opendir);
1186 #endif
1187   return closedir (dir);
1188 }
1189 #endif
1190
1191 #ifdef WRAP_readdir
1192 #include <dirent.h>
1193 WRAPPER2(struct dirent *, readdir, DIR *dir)
1194 {
1195   struct dirent *p;
1196   TRACE ("%s\n", __PRETTY_FUNCTION__);
1197   MF_VALIDATE_EXTENT (dir, 0, __MF_CHECK_READ, "readdir dir");
1198   p = readdir (dir);
1199   if (NULL != p) {
1200 #ifdef MF_REGISTER_readdir
1201     __mf_register (p, sizeof (*p), MF_REGISTER_readdir, "readdir result");
1202 #endif
1203     MF_VALIDATE_EXTENT (p, sizeof (*p), __MF_CHECK_WRITE, "readdir result");
1204   }
1205   return p;
1206 }
1207 #endif
1208
1209 #ifdef WRAP_recv
1210 #include <sys/socket.h>
1211 WRAPPER2(int, recv, int s, void *buf, size_t len, int flags)
1212 {
1213   TRACE ("%s\n", __PRETTY_FUNCTION__);
1214   MF_VALIDATE_EXTENT (buf, len, __MF_CHECK_WRITE, "recv buf");
1215   return recv (s, buf, len, flags);
1216 }
1217 #endif
1218
1219 #ifdef WRAP_recvfrom
1220 #include <sys/socket.h>
1221 WRAPPER2(int, recvfrom, int s, void *buf, size_t len, int flags,
1222                 struct sockaddr *from, socklen_t *fromlen)
1223 {
1224   TRACE ("%s\n", __PRETTY_FUNCTION__);
1225   MF_VALIDATE_EXTENT (buf, len, __MF_CHECK_WRITE, "recvfrom buf");
1226   MF_VALIDATE_EXTENT (from, (size_t)*fromlen, __MF_CHECK_WRITE,
1227     "recvfrom from");
1228   return recvfrom (s, buf, len, flags, from, fromlen);
1229 }
1230 #endif
1231
1232 #ifdef WRAP_recvmsg
1233 #include <sys/socket.h>
1234 WRAPPER2(int, recvmsg, int s, struct msghdr *msg, int flags)
1235 {
1236   TRACE ("%s\n", __PRETTY_FUNCTION__);
1237   MF_VALIDATE_EXTENT (msg, sizeof (*msg), __MF_CHECK_WRITE, "recvmsg msg");
1238   return recvmsg (s, msg, flags);
1239 }
1240 #endif
1241
1242 #ifdef WRAP_send
1243 #include <sys/socket.h>
1244 WRAPPER2(int, send, int s, const void *msg, size_t len, int flags)
1245 {
1246   TRACE ("%s\n", __PRETTY_FUNCTION__);
1247   MF_VALIDATE_EXTENT (msg, len, __MF_CHECK_READ, "send msg");
1248   return send (s, msg, len, flags);
1249 }
1250 #endif
1251
1252 #ifdef WRAP_sendto
1253 #include <sys/socket.h>
1254 WRAPPER2(int, sendto, int s, const void *msg, size_t len, int flags,
1255                 const struct sockaddr *to, socklen_t tolen)
1256 {
1257   TRACE ("%s\n", __PRETTY_FUNCTION__);
1258   MF_VALIDATE_EXTENT (msg, len, __MF_CHECK_READ, "sendto msg");
1259   MF_VALIDATE_EXTENT (to, (size_t)tolen, __MF_CHECK_WRITE, "sendto to");
1260   return sendto (s, msg, len, flags, to, tolen);
1261 }
1262 #endif
1263
1264 #ifdef WRAP_sendmsg
1265 #include <sys/socket.h>
1266 WRAPPER2(int, sendmsg, int s, const void *msg, int flags)
1267 {
1268   TRACE ("%s\n", __PRETTY_FUNCTION__);
1269   MF_VALIDATE_EXTENT (msg, sizeof (*msg), __MF_CHECK_READ, "sendmsg msg");
1270   return sendmsg (s, msg, flags);
1271 }
1272 #endif
1273
1274 #ifdef WRAP_setsockopt
1275 #include <sys/socket.h>
1276 WRAPPER2(int, setsockopt, int s, int level, int optname, const void *optval,
1277         socklen_t optlen)
1278 {
1279   TRACE ("%s\n", __PRETTY_FUNCTION__);
1280   MF_VALIDATE_EXTENT (optval, (size_t)optlen, __MF_CHECK_READ,
1281     "setsockopt optval");
1282   return setsockopt (s, level, optname, optval, optlen);
1283 }
1284 #endif
1285
1286 #ifdef WRAP_getsockopt
1287 #include <sys/socket.h>
1288 WRAPPER2(int, getsockopt, int s, int level, int optname, void *optval,
1289                 socklen_t *optlen)
1290 {
1291   TRACE ("%s\n", __PRETTY_FUNCTION__);
1292   MF_VALIDATE_EXTENT (optval, (size_t)*optlen, __MF_CHECK_WRITE,
1293     "getsockopt optval");
1294   return getsockopt (s, level, optname, optval, optlen);
1295 }
1296 #endif
1297
1298 #ifdef WRAP_accept
1299 #include <sys/socket.h>
1300 WRAPPER2(int, accept, int s, struct  sockaddr *addr, socklen_t *addrlen)
1301 {
1302   TRACE ("%s\n", __PRETTY_FUNCTION__);
1303   MF_VALIDATE_EXTENT (addr, (size_t)*addrlen, __MF_CHECK_WRITE, "accept addr");
1304   return accept (s, addr, addrlen);
1305 }
1306 #endif
1307
1308 #ifdef WRAP_bind
1309 #include <sys/socket.h>
1310 WRAPPER2(int, bind, int sockfd, struct  sockaddr *addr, socklen_t addrlen)
1311 {
1312   TRACE ("%s\n", __PRETTY_FUNCTION__);
1313   MF_VALIDATE_EXTENT (addr, (size_t)addrlen, __MF_CHECK_WRITE, "bind addr");
1314   return bind (sockfd, addr, addrlen);
1315 }
1316 #endif
1317
1318 #ifdef WRAP_connect
1319 #include <sys/socket.h>
1320 WRAPPER2(int, connect, int sockfd, const struct sockaddr  *addr,
1321         socklen_t addrlen)
1322 {
1323   TRACE ("%s\n", __PRETTY_FUNCTION__);
1324   MF_VALIDATE_EXTENT (addr, (size_t)addrlen, __MF_CHECK_READ,
1325     "connect addr");
1326   return connect (sockfd, addr, addrlen);
1327 }
1328 #endif
1329
1330 #ifdef WRAP_gethostname
1331 WRAPPER2(int, gethostname, char *name, size_t len)
1332 {
1333   TRACE ("%s\n", __PRETTY_FUNCTION__);
1334   MF_VALIDATE_EXTENT (name, len, __MF_CHECK_WRITE, "gethostname name");
1335   return gethostname (name, len);
1336 }
1337 #endif
1338
1339 #ifdef WRAP_sethostname
1340 WRAPPER2(int, sethostname, const char *name, size_t len)
1341 {
1342   TRACE ("%s\n", __PRETTY_FUNCTION__);
1343   MF_VALIDATE_EXTENT (name, len, __MF_CHECK_READ, "sethostname name");
1344   return sethostname (name, len);
1345 }
1346 #endif
1347
1348 #ifdef WRAP_gethostbyname
1349 #include <netdb.h>
1350 WRAPPER2(struct hostent *, gethostbyname, const char *name)
1351 {
1352   struct hostent *p;
1353   char **ss;
1354   char *s;
1355   size_t n;
1356   int nreg;
1357   TRACE ("%s\n", __PRETTY_FUNCTION__);
1358   n = strlen (name);
1359   MF_VALIDATE_EXTENT (name, CLAMPADD(n, 1), __MF_CHECK_READ,
1360     "gethostbyname name");
1361   p = gethostbyname (name);
1362   if (NULL != p) {
1363 #ifdef MF_REGISTER_gethostbyname
1364     __mf_register (p, sizeof (*p), MF_REGISTER_gethostbyname,
1365       "gethostbyname result");
1366 #endif
1367     MF_VALIDATE_EXTENT (p, sizeof (*p), __MF_CHECK_WRITE,
1368       "gethostbyname result");
1369     if (NULL != (s = p->h_name)) {
1370       n = strlen (s);
1371       n = CLAMPADD(n, 1);
1372 #ifdef MF_REGISTER_gethostbyname_items
1373       __mf_register (s, n, MF_REGISTER_gethostbyname_items,
1374         "gethostbyname result->h_name");
1375 #endif
1376       MF_VALIDATE_EXTENT (s, n, __MF_CHECK_WRITE,
1377         "gethostbyname result->h_name");
1378     }
1379
1380     if (NULL != (ss = p->h_aliases)) {
1381       for (nreg = 1;; ++nreg) {
1382         s = *ss++;
1383         if (NULL == s)
1384           break;
1385         n = strlen (s);
1386         n = CLAMPADD(n, 1);
1387 #ifdef MF_REGISTER_gethostbyname_items
1388         __mf_register (s, n, MF_REGISTER_gethostbyname_items,
1389           "gethostbyname result->h_aliases[]");
1390 #endif
1391         MF_VALIDATE_EXTENT (s, n, __MF_CHECK_WRITE,
1392           "gethostbyname result->h_aliases[]");
1393       }
1394       nreg *= sizeof (*p->h_aliases);
1395 #ifdef MF_REGISTER_gethostbyname_items
1396       __mf_register (p->h_aliases, nreg, MF_REGISTER_gethostbyname_items,
1397         "gethostbyname result->h_aliases");
1398 #endif
1399       MF_VALIDATE_EXTENT (p->h_aliases, nreg, __MF_CHECK_WRITE,
1400         "gethostbyname result->h_aliases");
1401     }
1402
1403     if (NULL != (ss = p->h_addr_list)) {
1404       for (nreg = 1;; ++nreg) {
1405         s = *ss++;
1406         if (NULL == s)
1407           break;
1408 #ifdef MF_REGISTER_gethostbyname_items
1409         __mf_register (s, p->h_length, MF_REGISTER_gethostbyname_items,
1410           "gethostbyname result->h_addr_list[]");
1411 #endif
1412         MF_VALIDATE_EXTENT (s, p->h_length, __MF_CHECK_WRITE,
1413           "gethostbyname result->h_addr_list[]");
1414       }
1415       nreg *= sizeof (*p->h_addr_list);
1416 #ifdef MF_REGISTER_gethostbyname_items
1417       __mf_register (p->h_addr_list, nreg, MF_REGISTER_gethostbyname_items,
1418         "gethostbyname result->h_addr_list");
1419 #endif
1420       MF_VALIDATE_EXTENT (p->h_addr_list, nreg, __MF_CHECK_WRITE,
1421         "gethostbyname result->h_addr_list");
1422     }
1423   }
1424   return p;
1425 }
1426 #endif
1427
1428 #ifdef WRAP_wait
1429 #include <sys/wait.h>
1430 WRAPPER2(pid_t, wait, int *status)
1431 {
1432   TRACE ("%s\n", __PRETTY_FUNCTION__);
1433   if (NULL != status)
1434     MF_VALIDATE_EXTENT (status, sizeof (*status), __MF_CHECK_WRITE,
1435       "wait status");
1436   return wait (status);
1437 }
1438 #endif
1439
1440 #ifdef WRAP_waitpid
1441 #include <sys/wait.h>
1442 WRAPPER2(pid_t, waitpid, pid_t pid, int *status, int options)
1443 {
1444   TRACE ("%s\n", __PRETTY_FUNCTION__);
1445   if (NULL != status)
1446     MF_VALIDATE_EXTENT (status, sizeof (*status), __MF_CHECK_WRITE,
1447       "waitpid status");
1448   return waitpid (pid, status, options);
1449 }
1450 #endif
1451
1452 #ifdef WRAP_popen
1453 WRAPPER2(FILE *, popen, const char *command, const char *mode)
1454 {
1455   size_t n;
1456   FILE *p;
1457   TRACE ("%s\n", __PRETTY_FUNCTION__);
1458
1459   n = strlen (command);
1460   MF_VALIDATE_EXTENT (command, CLAMPADD(n, 1), __MF_CHECK_READ, "popen path");
1461
1462   n = strlen (mode);
1463   MF_VALIDATE_EXTENT (mode, CLAMPADD(n, 1), __MF_CHECK_READ, "popen mode");
1464
1465   p = popen (command, mode);
1466   if (NULL != p) {
1467 #ifdef MF_REGISTER_fopen
1468     __mf_register (p, sizeof (*p), MF_REGISTER_fopen, "popen result");
1469 #endif
1470     MF_VALIDATE_EXTENT (p, sizeof (*p), __MF_CHECK_WRITE, "popen result");
1471   }
1472   return p;
1473 }
1474 #endif
1475
1476 #ifdef WRAP_pclose
1477 WRAPPER2(int, pclose, FILE *stream)
1478 {
1479   int resp;
1480   TRACE ("%s\n", __PRETTY_FUNCTION__);
1481   MF_VALIDATE_EXTENT (stream, sizeof (*stream), __MF_CHECK_WRITE,
1482     "pclose stream");
1483   resp = pclose (stream);
1484 #ifdef MF_REGISTER_fopen
1485   __mf_unregister (stream, sizeof (*stream));
1486 #endif
1487   return resp;
1488 }
1489 #endif
1490
1491 #ifdef WRAP_execve
1492 WRAPPER2(int, execve, const char *path, char *const argv [],
1493         char *const envp[])
1494 {
1495   size_t n;
1496   char *const *p;
1497   const char *s;
1498   TRACE ("%s\n", __PRETTY_FUNCTION__);
1499
1500   n = strlen (path);
1501   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "execve path");
1502
1503   for (p = argv;;) {
1504     MF_VALIDATE_EXTENT (p, sizeof (*p), __MF_CHECK_READ, "execve *argv");
1505     s = *p++;
1506     if (NULL == s)
1507       break;
1508     n = strlen (s);
1509     MF_VALIDATE_EXTENT (s, CLAMPADD(n, 1), __MF_CHECK_READ, "execve **argv");
1510   }
1511
1512   for (p = envp;;) {
1513     MF_VALIDATE_EXTENT (p, sizeof (*p), __MF_CHECK_READ, "execve *envp");
1514     s = *p++;
1515     if (NULL == s)
1516       break;
1517     n = strlen (s);
1518     MF_VALIDATE_EXTENT (s, CLAMPADD(n, 1), __MF_CHECK_READ, "execve **envp");
1519   }
1520   return execve (path, argv, envp);
1521 }
1522 #endif
1523
1524 #ifdef WRAP_execv
1525 WRAPPER2(int, execv, const char *path, char *const argv [])
1526 {
1527   size_t n;
1528   char *const *p;
1529   const char *s;
1530   TRACE ("%s\n", __PRETTY_FUNCTION__);
1531
1532   n = strlen (path);
1533   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "execv path");
1534
1535   for (p = argv;;) {
1536     MF_VALIDATE_EXTENT (p, sizeof (*p), __MF_CHECK_READ, "execv *argv");
1537     s = *p++;
1538     if (NULL == s)
1539       break;
1540     n = strlen (s);
1541     MF_VALIDATE_EXTENT (s, CLAMPADD(n, 1), __MF_CHECK_READ, "execv **argv");
1542   }
1543   return execv (path, argv);
1544 }
1545 #endif
1546
1547 #ifdef WRAP_execvp
1548 WRAPPER2(int, execvp, const char *path, char *const argv [])
1549 {
1550   size_t n;
1551   char *const *p;
1552   const char *s;
1553   TRACE ("%s\n", __PRETTY_FUNCTION__);
1554
1555   n = strlen (path);
1556   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "execvp path");
1557
1558   for (p = argv;;) {
1559     MF_VALIDATE_EXTENT (p, sizeof (*p), __MF_CHECK_READ, "execvp *argv");
1560     s = *p++;
1561     if (NULL == s)
1562       break;
1563     n = strlen (s);
1564     MF_VALIDATE_EXTENT (s, CLAMPADD(n, 1), __MF_CHECK_READ, "execvp **argv");
1565   }
1566   return execvp (path, argv);
1567 }
1568 #endif
1569
1570 #ifdef WRAP_system
1571 WRAPPER2(int, system, const char *string)
1572 {
1573   size_t n;
1574   TRACE ("%s\n", __PRETTY_FUNCTION__);
1575   n = strlen (string);
1576   MF_VALIDATE_EXTENT (string, CLAMPADD(n, 1), __MF_CHECK_READ,
1577     "system string");
1578   return system (string);
1579 }
1580 #endif
1581
1582 #ifdef WRAP_dlopen
1583 WRAPPER2(void *, dlopen, const char *path, int flags)
1584 {
1585   void *p;
1586   size_t n;
1587   TRACE ("%s\n", __PRETTY_FUNCTION__);
1588   n = strlen (path);
1589   MF_VALIDATE_EXTENT (path, CLAMPADD(n, 1), __MF_CHECK_READ, "dlopen path");
1590   p = dlopen (path, flags);
1591   if (NULL != p) {
1592 #ifdef MF_REGISTER_dlopen
1593     __mf_register (p, 0, MF_REGISTER_dlopen, "dlopen result");
1594 #endif
1595     MF_VALIDATE_EXTENT (p, 0, __MF_CHECK_WRITE, "dlopen result");
1596   }
1597   return p;
1598 }
1599 #endif
1600
1601 #ifdef WRAP_dlclose
1602 WRAPPER2(int, dlclose, void *handle)
1603 {
1604   int resp;
1605   TRACE ("%s\n", __PRETTY_FUNCTION__);
1606   MF_VALIDATE_EXTENT (handle, 0, __MF_CHECK_READ, "dlclose handle");
1607   resp = dlclose (handle);
1608 #ifdef MF_REGISTER_dlopen
1609   __mf_unregister (handle, 0);
1610 #endif
1611   return resp;
1612 }
1613 #endif
1614
1615 #ifdef WRAP_dlerror
1616 WRAPPER2(char *, dlerror)
1617 {
1618   char *p;
1619   TRACE ("%s\n", __PRETTY_FUNCTION__);
1620   p = dlerror ();
1621   if (NULL != p) {
1622     size_t n;
1623     n = strlen (p);
1624     n = CLAMPADD(n, 1);
1625 #ifdef MF_REGISTER_dlerror
1626     __mf_register (p, n, MF_REGISTER_dlerror, "dlerror result");
1627 #endif
1628     MF_VALIDATE_EXTENT (p, n, __MF_CHECK_WRITE, "dlerror result");
1629   }
1630   return p;
1631 }
1632 #endif
1633
1634 #ifdef WRAP_dlsym
1635 WRAPPER2(void *, dlsym, void *handle, char *symbol)
1636 {
1637   size_t n;
1638   void *p;
1639   TRACE ("%s\n", __PRETTY_FUNCTION__);
1640   MF_VALIDATE_EXTENT (handle, 0, __MF_CHECK_READ, "dlsym handle");
1641   n = strlen (symbol);
1642   MF_VALIDATE_EXTENT (symbol, CLAMPADD(n, 1), __MF_CHECK_READ, "dlsym symbol");
1643   p = dlsym (handle, symbol);
1644   if (NULL != p) {
1645 #ifdef MF_REGISTER_dlsym
1646     __mf_register (p, 0, MF_REGISTER_dlsym, "dlsym result");
1647 #endif
1648     MF_VALIDATE_EXTENT (p, 0, __MF_CHECK_WRITE, "dlsym result");
1649   }
1650   return p;
1651 }
1652 #endif
1653
1654 #ifdef WRAP_semop
1655 #include <sys/ipc.h>
1656 #include <sys/sem.h>
1657 WRAPPER2(int, semop, int semid, struct sembuf *sops, unsigned nsops)
1658 {
1659   TRACE ("%s\n", __PRETTY_FUNCTION__);
1660   MF_VALIDATE_EXTENT (sops, sizeof (*sops) * nsops, __MF_CHECK_READ,
1661     "semop sops");
1662   return semop (semid, sops, nsops);
1663 }
1664 #endif
1665
1666 #ifdef WRAP_semctl
1667 #include <sys/ipc.h>
1668 #include <sys/sem.h>
1669 #ifndef HAVE_UNION_SEMUN
1670 union semun {
1671         int val;                        /* value for SETVAL */
1672         struct semid_ds *buf;           /* buffer for IPC_STAT, IPC_SET */
1673         unsigned short int *array;      /* array for GETALL, SETALL */
1674         struct seminfo *__buf;          /* buffer for IPC_INFO */
1675 };
1676 #endif
1677 WRAPPER2(int, semctl, int semid, int semnum, int cmd, union semun arg)
1678 {
1679   TRACE ("%s\n", __PRETTY_FUNCTION__);
1680   switch (cmd) {
1681   case IPC_STAT:
1682     MF_VALIDATE_EXTENT (arg.buf, sizeof (*arg.buf), __MF_CHECK_WRITE,
1683       "semctl buf");
1684     break;
1685   case IPC_SET:
1686     MF_VALIDATE_EXTENT (arg.buf, sizeof (*arg.buf), __MF_CHECK_READ,
1687       "semctl buf");
1688     break;
1689   case GETALL:
1690     MF_VALIDATE_EXTENT (arg.array, sizeof (*arg.array), __MF_CHECK_WRITE,
1691       "semctl array");
1692   case SETALL:
1693     MF_VALIDATE_EXTENT (arg.array, sizeof (*arg.array), __MF_CHECK_READ,
1694       "semctl array");
1695     break;
1696 #ifdef IPC_INFO
1697   /* FreeBSD 5.1 headers include IPC_INFO but not the __buf field.  */
1698 #if !defined(__FreeBSD__)
1699   case IPC_INFO:
1700     MF_VALIDATE_EXTENT (arg.__buf, sizeof (*arg.__buf), __MF_CHECK_WRITE,
1701       "semctl __buf");
1702     break;
1703 #endif
1704 #endif
1705   default:
1706     break;
1707   }
1708   return semctl (semid, semnum, cmd, arg);
1709 }
1710 #endif
1711
1712 #ifdef WRAP_shmctl
1713 #include <sys/ipc.h>
1714 #include <sys/shm.h>
1715 WRAPPER2(int, shmctl, int shmid, int cmd, struct shmid_ds *buf)
1716 {
1717   TRACE ("%s\n", __PRETTY_FUNCTION__);
1718   switch (cmd) {
1719   case IPC_STAT:
1720     MF_VALIDATE_EXTENT (buf, sizeof (*buf), __MF_CHECK_WRITE,
1721       "shmctl buf");
1722     break;
1723   case IPC_SET:
1724     MF_VALIDATE_EXTENT (buf, sizeof (*buf), __MF_CHECK_READ,
1725       "shmctl buf");
1726     break;
1727   default:
1728     break;
1729   }
1730   return shmctl (shmid, cmd, buf);
1731 }
1732 #endif
1733
1734 #ifdef WRAP_shmat
1735 #include <sys/ipc.h>
1736 #include <sys/shm.h>
1737 WRAPPER2(void *, shmat, int shmid, const void *shmaddr, int shmflg)
1738 {
1739   void *p;
1740   TRACE ("%s\n", __PRETTY_FUNCTION__);
1741   p = shmat (shmid, shmaddr, shmflg);
1742 #ifdef MF_REGISTER_shmat
1743   if (NULL != p) {
1744     struct shmid_ds buf;
1745     __mf_register (p, shmctl (shmid, IPC_STAT, &buf) ? 0 : buf.shm_segsz,
1746       MF_REGISTER_shmat, "shmat result");
1747   }
1748 #endif
1749   return p;
1750 }
1751 #endif
1752
1753 #ifdef WRAP_shmdt
1754 #include <sys/ipc.h>
1755 #include <sys/shm.h>
1756 WRAPPER2(int, shmdt, const void *shmaddr)
1757 {
1758   int resp;
1759   TRACE ("%s\n", __PRETTY_FUNCTION__);
1760   resp = shmdt (shmaddr);
1761 #ifdef MF_REGISTER_shmat
1762   __mf_unregister ((void *)shmaddr, 0);
1763 #endif
1764   return resp;
1765 }
1766 #endif
1767