sanitizer_common_interceptors.inc revision 0a2cc37712a452525f9f03b3bf67b1f0a97c8d3a
14f32c0beaa83ffbb84db23d2e6205bee57c39ce1Evgeniy Stepanov//===-- sanitizer_common_interceptors.inc -----------------------*- C++ -*-===//
28530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany//
38530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany//                     The LLVM Compiler Infrastructure
48530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany//
58530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany// This file is distributed under the University of Illinois Open Source
68530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany// License. See LICENSE.TXT for details.
78530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany//
88530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany//===----------------------------------------------------------------------===//
98530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany//
108530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany// Common function interceptors for tools like AddressSanitizer,
118530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany// ThreadSanitizer, MemorySanitizer, etc.
128530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany//
138530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany// This file should be included into the tool's interceptor file,
148530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany// which has to define it's own macros:
158530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany//   COMMON_INTERCEPTOR_ENTER
168530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany//   COMMON_INTERCEPTOR_READ_RANGE
178530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany//   COMMON_INTERCEPTOR_WRITE_RANGE
18c8033193376c3326478a345c4ae6633d4d2862c6Kostya Serebryany//   COMMON_INTERCEPTOR_FD_ACQUIRE
19c8033193376c3326478a345c4ae6633d4d2862c6Kostya Serebryany//   COMMON_INTERCEPTOR_FD_RELEASE
20c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany//   COMMON_INTERCEPTOR_SET_THREAD_NAME
218530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany//===----------------------------------------------------------------------===//
226afa1b0406f5cce7256d4f8717bfe394a16999b5Kostya Serebryany#include "interception/interception.h"
2374737d595c4e3638b980bd88b0492247ae4318faAlexey Samsonov#include "sanitizer_platform_interceptors.h"
24b1cc4e448f35515e737ac4969aaa04f3fa3af10aKostya Serebryany
25996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov#include <stdarg.h>
26996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
2730e110edf92303237d471f1cb8e3ad07954fb145Evgeniy Stepanov#if SANITIZER_WINDOWS
28348bd12af55f560e0822e753788d8a51fa050c3fEvgeniy Stepanov#define va_copy(dst, src) ((dst) = (src))
29348bd12af55f560e0822e753788d8a51fa050c3fEvgeniy Stepanov#endif // _WIN32
30348bd12af55f560e0822e753788d8a51fa050c3fEvgeniy Stepanov
31be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov#if SANITIZER_INTERCEPT_STRCASECMP
32be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukovstatic inline int CharCaseCmp(unsigned char c1, unsigned char c2) {
33be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  int c1_low = ToLower(c1);
34be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  int c2_low = ToLower(c2);
35be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  return c1_low - c2_low;
36be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov}
37be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov
38be52366ff2500f11133fd6089f349e93bd5f4822Dmitry VyukovINTERCEPTOR(int, strcasecmp, const char *s1, const char *s2) {
39be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  void *ctx;
40be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  COMMON_INTERCEPTOR_ENTER(ctx, strcasecmp, s1, s2);
41be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  unsigned char c1 = 0, c2 = 0;
42be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  uptr i;
43be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  for (i = 0; ; i++) {
44be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov    c1 = (unsigned char)s1[i];
45be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov    c2 = (unsigned char)s2[i];
46be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov    if (CharCaseCmp(c1, c2) != 0 || c1 == '\0')
47be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov      break;
48be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  }
49be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  COMMON_INTERCEPTOR_READ_RANGE(ctx, s1, i + 1);
50be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  COMMON_INTERCEPTOR_READ_RANGE(ctx, s2, i + 1);
51be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  return CharCaseCmp(c1, c2);
52be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov}
53be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov
54be52366ff2500f11133fd6089f349e93bd5f4822Dmitry VyukovINTERCEPTOR(int, strncasecmp, const char *s1, const char *s2, SIZE_T n) {
55be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  void *ctx;
56be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  COMMON_INTERCEPTOR_ENTER(ctx, strncasecmp, s1, s2, n);
57be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  unsigned char c1 = 0, c2 = 0;
58be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  uptr i;
59be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  for (i = 0; i < n; i++) {
60be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov    c1 = (unsigned char)s1[i];
61be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov    c2 = (unsigned char)s2[i];
62be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov    if (CharCaseCmp(c1, c2) != 0 || c1 == '\0')
63be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov      break;
64be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  }
65be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  COMMON_INTERCEPTOR_READ_RANGE(ctx, s1, Min(i + 1, n));
66be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  COMMON_INTERCEPTOR_READ_RANGE(ctx, s2, Min(i + 1, n));
67be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov  return CharCaseCmp(c1, c2);
68be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov}
69be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov
70be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov#define INIT_STRCASECMP INTERCEPT_FUNCTION(strcasecmp)
71be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov#define INIT_STRNCASECMP INTERCEPT_FUNCTION(strncasecmp)
72be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov#else
73be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov#define INIT_STRCASECMP
74be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov#define INIT_STRNCASECMP
75be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov#endif
76be52366ff2500f11133fd6089f349e93bd5f4822Dmitry Vyukov
777cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov#if SANITIZER_INTERCEPT_FREXP
787cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy StepanovINTERCEPTOR(double, frexp, double x, int *exp) {
797cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  void *ctx;
807cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, frexp, x, exp);
817cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  double res = REAL(frexp)(x, exp);
827cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  COMMON_INTERCEPTOR_WRITE_RANGE(ctx, exp, sizeof(*exp));
837cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  return res;
847cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov}
857cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov
86ff5d1fcdd74036fa15d96fafd487397ebf5f202eAlexey Samsonov#define INIT_FREXP INTERCEPT_FUNCTION(frexp);
87ff5d1fcdd74036fa15d96fafd487397ebf5f202eAlexey Samsonov#else
88ff5d1fcdd74036fa15d96fafd487397ebf5f202eAlexey Samsonov#define INIT_FREXP
89ff5d1fcdd74036fa15d96fafd487397ebf5f202eAlexey Samsonov#endif // SANITIZER_INTERCEPT_FREXP
90ff5d1fcdd74036fa15d96fafd487397ebf5f202eAlexey Samsonov
91ff5d1fcdd74036fa15d96fafd487397ebf5f202eAlexey Samsonov#if SANITIZER_INTERCEPT_FREXPF_FREXPL
927cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy StepanovINTERCEPTOR(float, frexpf, float x, int *exp) {
937cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  void *ctx;
947cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, frexpf, x, exp);
957cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  float res = REAL(frexpf)(x, exp);
967cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  COMMON_INTERCEPTOR_WRITE_RANGE(ctx, exp, sizeof(*exp));
977cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  return res;
987cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov}
997cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov
1007cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy StepanovINTERCEPTOR(long double, frexpl, long double x, int *exp) {
1017cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  void *ctx;
1027cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, frexpl, x, exp);
1037cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  long double res = REAL(frexpl)(x, exp);
1047cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  COMMON_INTERCEPTOR_WRITE_RANGE(ctx, exp, sizeof(*exp));
1057cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  return res;
1067cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov}
1077cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov
108ff5d1fcdd74036fa15d96fafd487397ebf5f202eAlexey Samsonov#define INIT_FREXPF_FREXPL                       \
1097cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  INTERCEPT_FUNCTION(frexpf);                    \
1107cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov  INTERCEPT_FUNCTION(frexpl)
1117cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov#else
112ff5d1fcdd74036fa15d96fafd487397ebf5f202eAlexey Samsonov#define INIT_FREXPF_FREXPL
113ff5d1fcdd74036fa15d96fafd487397ebf5f202eAlexey Samsonov#endif // SANITIZER_INTERCEPT_FREXPF_FREXPL
1147cbbb2943527ff852bdace822c8592cfc7e450d7Evgeniy Stepanov
1158ffd87791a5376d44edfa288cbf469702edbfa22Alexey Samsonov#if SANITIZER_INTERCEPT_READ
1166afa1b0406f5cce7256d4f8717bfe394a16999b5Kostya SerebryanyINTERCEPTOR(SSIZE_T, read, int fd, void *ptr, SIZE_T count) {
11744be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov  void *ctx;
118996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, read, fd, ptr, count);
1196afa1b0406f5cce7256d4f8717bfe394a16999b5Kostya Serebryany  SSIZE_T res = REAL(read)(fd, ptr, count);
1208530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany  if (res > 0)
121996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, ptr, res);
122c8033193376c3326478a345c4ae6633d4d2862c6Kostya Serebryany  if (res >= 0 && fd >= 0)
123996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_FD_ACQUIRE(ctx, fd);
1248530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany  return res;
1258530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany}
12644be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_READ INTERCEPT_FUNCTION(read)
127c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany#else
12844be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_READ
1298ffd87791a5376d44edfa288cbf469702edbfa22Alexey Samsonov#endif
1308530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany
131c333dffb81f1d85483d657c254c17f636ab192c5Alexey Samsonov#if SANITIZER_INTERCEPT_PREAD
1326afa1b0406f5cce7256d4f8717bfe394a16999b5Kostya SerebryanyINTERCEPTOR(SSIZE_T, pread, int fd, void *ptr, SIZE_T count, OFF_T offset) {
13344be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov  void *ctx;
134996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, pread, fd, ptr, count, offset);
1356afa1b0406f5cce7256d4f8717bfe394a16999b5Kostya Serebryany  SSIZE_T res = REAL(pread)(fd, ptr, count, offset);
1368530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany  if (res > 0)
137996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, ptr, res);
138c8033193376c3326478a345c4ae6633d4d2862c6Kostya Serebryany  if (res >= 0 && fd >= 0)
139996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_FD_ACQUIRE(ctx, fd);
1408530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany  return res;
1418530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany}
14244be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_PREAD INTERCEPT_FUNCTION(pread)
143c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany#else
14444be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_PREAD
145c333dffb81f1d85483d657c254c17f636ab192c5Alexey Samsonov#endif
1468530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany
147b1cc4e448f35515e737ac4969aaa04f3fa3af10aKostya Serebryany#if SANITIZER_INTERCEPT_PREAD64
1486afa1b0406f5cce7256d4f8717bfe394a16999b5Kostya SerebryanyINTERCEPTOR(SSIZE_T, pread64, int fd, void *ptr, SIZE_T count, OFF64_T offset) {
14944be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov  void *ctx;
150996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, pread64, fd, ptr, count, offset);
1516afa1b0406f5cce7256d4f8717bfe394a16999b5Kostya Serebryany  SSIZE_T res = REAL(pread64)(fd, ptr, count, offset);
1528530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany  if (res > 0)
153996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, ptr, res);
154c8033193376c3326478a345c4ae6633d4d2862c6Kostya Serebryany  if (res >= 0 && fd >= 0)
155996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_FD_ACQUIRE(ctx, fd);
1568530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany  return res;
1578530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany}
15844be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_PREAD64 INTERCEPT_FUNCTION(pread64)
159c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany#else
16044be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_PREAD64
1611f5e23e3204961456d4c7a9b45060597d4ff69afAlexander Potapenko#endif
1628530e2b953f0b34ecd267a6aba5f155d5c08c5c8Kostya Serebryany
163c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany#if SANITIZER_INTERCEPT_WRITE
164c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya SerebryanyINTERCEPTOR(SSIZE_T, write, int fd, void *ptr, SIZE_T count) {
16544be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov  void *ctx;
166996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, write, fd, ptr, count);
167c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  if (fd >= 0)
168996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_FD_RELEASE(ctx, fd);
169c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  SSIZE_T res = REAL(write)(fd, ptr, count);
170c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  if (res > 0)
171996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, ptr, res);
172c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  return res;
173c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany}
17444be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_WRITE INTERCEPT_FUNCTION(write)
175153ba3f41d8f6ad1641ae76cfdf01445cec9db89Kostya Serebryany#else
17644be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_WRITE
177153ba3f41d8f6ad1641ae76cfdf01445cec9db89Kostya Serebryany#endif
178153ba3f41d8f6ad1641ae76cfdf01445cec9db89Kostya Serebryany
179c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany#if SANITIZER_INTERCEPT_PWRITE
180f0c846b8ef61a5f4bc664c463d643bb8dedc3768Dmitry VyukovINTERCEPTOR(SSIZE_T, pwrite, int fd, void *ptr, SIZE_T count, OFF_T offset) {
18144be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov  void *ctx;
182f0c846b8ef61a5f4bc664c463d643bb8dedc3768Dmitry Vyukov  COMMON_INTERCEPTOR_ENTER(ctx, pwrite, fd, ptr, count, offset);
183c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  if (fd >= 0)
184996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_FD_RELEASE(ctx, fd);
185f0c846b8ef61a5f4bc664c463d643bb8dedc3768Dmitry Vyukov  SSIZE_T res = REAL(pwrite)(fd, ptr, count, offset);
186c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  if (res > 0)
187996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, ptr, res);
188c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  return res;
189c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany}
19044be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_PWRITE INTERCEPT_FUNCTION(pwrite)
191153ba3f41d8f6ad1641ae76cfdf01445cec9db89Kostya Serebryany#else
19244be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_PWRITE
193153ba3f41d8f6ad1641ae76cfdf01445cec9db89Kostya Serebryany#endif
194153ba3f41d8f6ad1641ae76cfdf01445cec9db89Kostya Serebryany
195c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany#if SANITIZER_INTERCEPT_PWRITE64
196f0c846b8ef61a5f4bc664c463d643bb8dedc3768Dmitry VyukovINTERCEPTOR(SSIZE_T, pwrite64, int fd, void *ptr, OFF64_T count,
197f0c846b8ef61a5f4bc664c463d643bb8dedc3768Dmitry Vyukov            OFF64_T offset) {
19844be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov  void *ctx;
199f0c846b8ef61a5f4bc664c463d643bb8dedc3768Dmitry Vyukov  COMMON_INTERCEPTOR_ENTER(ctx, pwrite64, fd, ptr, count, offset);
200c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  if (fd >= 0)
201996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_FD_RELEASE(ctx, fd);
202f0c846b8ef61a5f4bc664c463d643bb8dedc3768Dmitry Vyukov  SSIZE_T res = REAL(pwrite64)(fd, ptr, count, offset);
203c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  if (res > 0)
204996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, ptr, res);
205c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  return res;
206c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany}
20744be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_PWRITE64 INTERCEPT_FUNCTION(pwrite64)
208153ba3f41d8f6ad1641ae76cfdf01445cec9db89Kostya Serebryany#else
20944be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_PWRITE64
210153ba3f41d8f6ad1641ae76cfdf01445cec9db89Kostya Serebryany#endif
211153ba3f41d8f6ad1641ae76cfdf01445cec9db89Kostya Serebryany
212c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany#if SANITIZER_INTERCEPT_PRCTL
21369b109a665247d424874253b412fe9b5253d1702Evgeniy StepanovINTERCEPTOR(int, prctl, int option,
21469b109a665247d424874253b412fe9b5253d1702Evgeniy Stepanov            unsigned long arg2, unsigned long arg3,   // NOLINT
21544be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov            unsigned long arg4, unsigned long arg5) { // NOLINT
21644be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov  void *ctx;
217996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, prctl, option, arg2, arg3, arg4, arg5);
218c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  static const int PR_SET_NAME = 15;
219c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  int res = REAL(prctl(option, arg2, arg3, arg4, arg5));
220c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  if (option == PR_SET_NAME) {
221c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany    char buff[16];
22244be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov    internal_strncpy(buff, (char *)arg2, 15);
223c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany    buff[15] = 0;
224996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov    COMMON_INTERCEPTOR_SET_THREAD_NAME(ctx, buff);
225c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  }
226c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany  return res;
227c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany}
22844be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_PRCTL INTERCEPT_FUNCTION(prctl)
229c20b321d49f0eff60f1394d56e623d8ca94f24d7Kostya Serebryany#else
23044be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_PRCTL
23144be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#endif // SANITIZER_INTERCEPT_PRCTL
232996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
233fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov
234fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov#if SANITIZER_INTERCEPT_TIME
235fef660506e9e5703fedfee01d614abd4b741c738Evgeniy StepanovINTERCEPTOR(unsigned long, time, unsigned long *t) {
236fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov  void *ctx;
237fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, time, t);
238fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov  unsigned long res = REAL(time)(t);
23915832c2afc4f04fa558160441d1b01fb3f0ec08bAlexander Potapenko  if (t && res != (unsigned long)-1) {
240fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, t, sizeof(*t));
241fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov  }
242fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov  return res;
243fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov}
244fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov#define INIT_TIME                                \
245fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov  INTERCEPT_FUNCTION(time);
246fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov#else
247fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov#define INIT_TIME
248fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov#endif // SANITIZER_INTERCEPT_TIME
249fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov
250fef660506e9e5703fedfee01d614abd4b741c738Evgeniy Stepanov
2519358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov#if SANITIZER_INTERCEPT_LOCALTIME_AND_FRIENDS
2529358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy StepanovINTERCEPTOR(void *, localtime, unsigned long *timep) {
2539358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *ctx;
2549358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, localtime, timep);
2559358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *res = REAL(localtime)(timep);
2569358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  if (res) {
2579358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, timep, sizeof(*timep));
2589358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, struct_tm_sz);
2599358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  }
2609358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  return res;
2619358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov}
2629358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy StepanovINTERCEPTOR(void *, localtime_r, unsigned long *timep, void *result) {
2639358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *ctx;
2649358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, localtime_r, timep, result);
2659358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *res = REAL(localtime_r)(timep, result);
2669358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  if (res) {
2679358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, timep, sizeof(*timep));
2689358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, struct_tm_sz);
2699358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  }
2709358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  return res;
2719358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov}
2729358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy StepanovINTERCEPTOR(void *, gmtime, unsigned long *timep) {
2739358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *ctx;
2749358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, gmtime, timep);
2759358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *res = REAL(gmtime)(timep);
2769358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  if (res) {
2779358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, timep, sizeof(*timep));
2789358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, struct_tm_sz);
2799358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  }
2809358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  return res;
2819358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov}
2829358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy StepanovINTERCEPTOR(void *, gmtime_r, unsigned long *timep, void *result) {
2839358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *ctx;
2849358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, gmtime_r, timep, result);
2859358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *res = REAL(gmtime_r)(timep, result);
2869358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  if (res) {
2879358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, timep, sizeof(*timep));
2889358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, struct_tm_sz);
2899358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  }
2909358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  return res;
2919358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov}
2929358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy StepanovINTERCEPTOR(char *, ctime, unsigned long *timep) {
2939358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *ctx;
2949358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, ctime, timep);
2959358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  char *res = REAL(ctime)(timep);
2969358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  if (res) {
2979358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, timep, sizeof(*timep));
2989358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, REAL(strlen)(res) + 1);
2999358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  }
3009358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  return res;
3019358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov}
3029358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy StepanovINTERCEPTOR(char *, ctime_r, unsigned long *timep, char *result) {
3039358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *ctx;
3049358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, ctime_r, timep, result);
3059358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  char *res = REAL(ctime_r)(timep, result);
3069358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  if (res) {
3079358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, timep, sizeof(*timep));
3089358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, REAL(strlen)(res) + 1);
3099358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  }
3109358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  return res;
3119358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov}
3129358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy StepanovINTERCEPTOR(char *, asctime, void *tm) {
3139358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *ctx;
3149358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, asctime, tm);
3159358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  char *res = REAL(asctime)(tm);
3169358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  if (res) {
3179358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, tm, struct_tm_sz);
3189358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, REAL(strlen)(res) + 1);
3199358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  }
3209358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  return res;
3219358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov}
3229358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy StepanovINTERCEPTOR(char *, asctime_r, void *tm, char *result) {
3239358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  void *ctx;
3249358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, asctime_r, tm, result);
3259358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  char *res = REAL(asctime_r)(tm, result);
3269358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  if (res) {
3279358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, tm, struct_tm_sz);
3289358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, REAL(strlen)(res) + 1);
3299358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  }
3309358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  return res;
3319358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov}
3329358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov#define INIT_LOCALTIME_AND_FRIENDS               \
3339358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  INTERCEPT_FUNCTION(localtime);                 \
3349358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  INTERCEPT_FUNCTION(localtime_r);               \
3359358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  INTERCEPT_FUNCTION(gmtime);                    \
3369358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  INTERCEPT_FUNCTION(gmtime_r);                  \
3379358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  INTERCEPT_FUNCTION(ctime);                     \
3389358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  INTERCEPT_FUNCTION(ctime_r);                   \
3399358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  INTERCEPT_FUNCTION(asctime);                   \
3409358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov  INTERCEPT_FUNCTION(asctime_r);
3419358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov#else
3429358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov#define INIT_LOCALTIME_AND_FRIENDS
3439358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov#endif // SANITIZER_INTERCEPT_LOCALTIME_AND_FRIENDS
3449358c58d0aaf1b20f17362af354d4c3c1309276aEvgeniy Stepanov
345996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov#if SANITIZER_INTERCEPT_SCANF
346996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
3474f32c0beaa83ffbb84db23d2e6205bee57c39ce1Evgeniy Stepanov#include "sanitizer_common_interceptors_scanf.inc"
348996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
349c5b4e86e848758856433da2e876c473dd31db55cEvgeniy Stepanov#define VSCANF_INTERCEPTOR_IMPL(vname, allowGnuMalloc, ...)                    \
3504ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  {                                                                            \
3514ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    void *ctx;                                                                 \
3524ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    COMMON_INTERCEPTOR_ENTER(ctx, vname, __VA_ARGS__);                         \
3534ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    va_list aq;                                                                \
3544ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    va_copy(aq, ap);                                                           \
3554ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    int res = REAL(vname)(__VA_ARGS__);                                        \
3564ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    if (res > 0)                                                               \
357c5b4e86e848758856433da2e876c473dd31db55cEvgeniy Stepanov      scanf_common(ctx, res, allowGnuMalloc, format, aq);                      \
3584ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    va_end(aq);                                                                \
3594ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    return res;                                                                \
3604ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  }
361996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
3624ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, vscanf, const char *format, va_list ap)
363c5b4e86e848758856433da2e876c473dd31db55cEvgeniy StepanovVSCANF_INTERCEPTOR_IMPL(vscanf, true, format, ap)
364996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
3654ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, vsscanf, const char *str, const char *format, va_list ap)
366c5b4e86e848758856433da2e876c473dd31db55cEvgeniy StepanovVSCANF_INTERCEPTOR_IMPL(vsscanf, true, str, format, ap)
367996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
3684ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, vfscanf, void *stream, const char *format, va_list ap)
369c5b4e86e848758856433da2e876c473dd31db55cEvgeniy StepanovVSCANF_INTERCEPTOR_IMPL(vfscanf, true, stream, format, ap)
370996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
3719eab858dfd995cb0432efa18edbcd0e791114be9Alexander Potapenko#if SANITIZER_INTERCEPT_ISOC99_SCANF
3724ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, __isoc99_vscanf, const char *format, va_list ap)
373c5b4e86e848758856433da2e876c473dd31db55cEvgeniy StepanovVSCANF_INTERCEPTOR_IMPL(__isoc99_vscanf, false, format, ap)
374996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
3754ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, __isoc99_vsscanf, const char *str, const char *format,
3764ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov            va_list ap)
377c5b4e86e848758856433da2e876c473dd31db55cEvgeniy StepanovVSCANF_INTERCEPTOR_IMPL(__isoc99_vsscanf, false, str, format, ap)
3784ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov
3794ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, __isoc99_vfscanf, void *stream, const char *format, va_list ap)
380c5b4e86e848758856433da2e876c473dd31db55cEvgeniy StepanovVSCANF_INTERCEPTOR_IMPL(__isoc99_vfscanf, false, stream, format, ap)
3819eab858dfd995cb0432efa18edbcd0e791114be9Alexander Potapenko#endif  // SANITIZER_INTERCEPT_ISOC99_SCANF
3824ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov
3834ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov#define SCANF_INTERCEPTOR_IMPL(name, vname, ...)                               \
3844ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  {                                                                            \
3854ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    void *ctx;                                                                 \
3864ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    COMMON_INTERCEPTOR_ENTER(ctx, name, __VA_ARGS__);                          \
3874ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    va_list ap;                                                                \
3884ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    va_start(ap, format);                                                      \
3894ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    int res = vname(__VA_ARGS__, ap);                                          \
3904ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    va_end(ap);                                                                \
3914ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov    return res;                                                                \
3924ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  }
3934ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov
3944ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, scanf, const char *format, ...)
3954ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovSCANF_INTERCEPTOR_IMPL(scanf, vscanf, format)
3964ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov
3974ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, fscanf, void *stream, const char *format, ...)
3984ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovSCANF_INTERCEPTOR_IMPL(fscanf, vfscanf, stream, format)
3994ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov
4004ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, sscanf, const char *str, const char *format, ...)
4014ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovSCANF_INTERCEPTOR_IMPL(sscanf, vsscanf, str, format)
4024ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov
4039eab858dfd995cb0432efa18edbcd0e791114be9Alexander Potapenko#if SANITIZER_INTERCEPT_ISOC99_SCANF
4044ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, __isoc99_scanf, const char *format, ...)
4054ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovSCANF_INTERCEPTOR_IMPL(__isoc99_scanf, __isoc99_vscanf, format)
4064ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov
4074ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, __isoc99_fscanf, void *stream, const char *format, ...)
4084ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovSCANF_INTERCEPTOR_IMPL(__isoc99_fscanf, __isoc99_vfscanf, stream, format)
4094ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov
4104ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovINTERCEPTOR(int, __isoc99_sscanf, const char *str, const char *format, ...)
4114ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy StepanovSCANF_INTERCEPTOR_IMPL(__isoc99_sscanf, __isoc99_vsscanf, str, format)
4129eab858dfd995cb0432efa18edbcd0e791114be9Alexander Potapenko#endif
413996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
41444be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov#define INIT_SCANF                                                             \
41544be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov  INTERCEPT_FUNCTION(scanf);                                                   \
4164ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  INTERCEPT_FUNCTION(sscanf);                                                  \
41744be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov  INTERCEPT_FUNCTION(fscanf);                                                  \
41844be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov  INTERCEPT_FUNCTION(vscanf);                                                  \
41944be70b186549d592c952a13aafe79bfeae89f81Evgeniy Stepanov  INTERCEPT_FUNCTION(vsscanf);                                                 \
4204ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  INTERCEPT_FUNCTION(vfscanf);                                                 \
4214ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  INTERCEPT_FUNCTION(__isoc99_scanf);                                          \
4224ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  INTERCEPT_FUNCTION(__isoc99_sscanf);                                         \
4234ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  INTERCEPT_FUNCTION(__isoc99_fscanf);                                         \
4244ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  INTERCEPT_FUNCTION(__isoc99_vscanf);                                         \
4254ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  INTERCEPT_FUNCTION(__isoc99_vsscanf);                                        \
4264ae1adb49f34cf9a9ef854cf04348531608f0eadEvgeniy Stepanov  INTERCEPT_FUNCTION(__isoc99_vfscanf);
427996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
428996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov#else
429996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov#define INIT_SCANF
430996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov#endif
431996c4f2fa53cce8f9d7b517073f38569460de505Evgeniy Stepanov
432103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov#if SANITIZER_INTERCEPT_GETPWNAM_AND_FRIENDS
433e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy StepanovINTERCEPTOR(void *, getpwnam, const char *name) {
434e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  void *ctx;
435e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, getpwnam, name);
436e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_READ_RANGE(ctx, name, REAL(strlen)(name) + 1);
437e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  void *res = REAL(getpwnam)(name);
438e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  if (res != 0)
439e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, struct_passwd_sz);
440e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  return res;
441e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov}
442e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy StepanovINTERCEPTOR(void *, getpwuid, u32 uid) {
443e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  void *ctx;
444e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, getpwuid, uid);
445e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  void *res = REAL(getpwuid)(uid);
446e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  if (res != 0)
447e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, struct_passwd_sz);
448e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  return res;
449e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov}
450103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy StepanovINTERCEPTOR(void *, getgrnam, const char *name) {
451103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  void *ctx;
452103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, getgrnam, name);
453103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  COMMON_INTERCEPTOR_READ_RANGE(ctx, name, REAL(strlen)(name) + 1);
454103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  void *res = REAL(getgrnam)(name);
455103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  if (res != 0)
456103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, struct_group_sz);
457103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  return res;
458103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov}
459103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy StepanovINTERCEPTOR(void *, getgrgid, u32 gid) {
460103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  void *ctx;
461103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, getgrgid, gid);
462103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  void *res = REAL(getgrgid)(gid);
463103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  if (res != 0)
464103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, struct_group_sz);
465103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  return res;
466103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov}
467103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov#define INIT_GETPWNAM_AND_FRIENDS                  \
468103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  INTERCEPT_FUNCTION(getpwnam);                    \
469103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  INTERCEPT_FUNCTION(getpwuid);                    \
470103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  INTERCEPT_FUNCTION(getgrnam);                    \
471103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  INTERCEPT_FUNCTION(getgrgid);
472e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#else
473103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov#define INIT_GETPWNAM_AND_FRIENDS
474e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#endif
475e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov
476e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov
477103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov#if SANITIZER_INTERCEPT_GETPWNAM_R_AND_FRIENDS
478e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy StepanovINTERCEPTOR(int, getpwnam_r, const char *name, void *pwd,
479e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    char *buf, SIZE_T buflen, void **result) {
480e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  void *ctx;
481e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, getpwnam_r, name, pwd, buf, buflen, result);
482e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_READ_RANGE(ctx, name, REAL(strlen)(name) + 1);
483e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  int res = REAL(getpwnam_r)(name, pwd, buf, buflen, result);
484e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  if (!res) {
485e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, pwd, struct_passwd_sz);
486e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, buf, buflen);
487e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  }
488e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  return res;
489e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov}
490e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy StepanovINTERCEPTOR(int, getpwuid_r, u32 uid, void *pwd,
491e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    char *buf, SIZE_T buflen, void **result) {
492e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  void *ctx;
493e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, getpwuid_r, uid, pwd, buf, buflen, result);
494e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  int res = REAL(getpwuid_r)(uid, pwd, buf, buflen, result);
495e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  if (!res) {
496e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, pwd, struct_passwd_sz);
497e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, buf, buflen);
498e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  }
499e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  return res;
500e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov}
501103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy StepanovINTERCEPTOR(int, getgrnam_r, const char *name, void *grp,
502103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov    char *buf, SIZE_T buflen, void **result) {
503103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  void *ctx;
504103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, getgrnam_r, name, grp, buf, buflen, result);
505103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  COMMON_INTERCEPTOR_READ_RANGE(ctx, name, REAL(strlen)(name) + 1);
506103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  int res = REAL(getgrnam_r)(name, grp, buf, buflen, result);
507103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  if (!res) {
508103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, grp, struct_group_sz);
509103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, buf, buflen);
510103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  }
511103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  return res;
512103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov}
513103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy StepanovINTERCEPTOR(int, getgrgid_r, u32 gid, void *grp,
514103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov    char *buf, SIZE_T buflen, void **result) {
515103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  void *ctx;
516103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, getgrgid_r, gid, grp, buf, buflen, result);
517103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  int res = REAL(getgrgid_r)(gid, grp, buf, buflen, result);
518103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  if (!res) {
519103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, grp, struct_group_sz);
520103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, buf, buflen);
521103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  }
522103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  return res;
523103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov}
524103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov#define INIT_GETPWNAM_R_AND_FRIENDS                \
525103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  INTERCEPT_FUNCTION(getpwnam_r);                  \
526103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  INTERCEPT_FUNCTION(getpwuid_r);                  \
527103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  INTERCEPT_FUNCTION(getgrnam_r);                  \
528103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov  INTERCEPT_FUNCTION(getgrgid_r);
529e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#else
530103a63ed3fb5511516b55ce1ee4f33290209f3d8Evgeniy Stepanov#define INIT_GETPWNAM_R_AND_FRIENDS
531e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#endif
532e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov
533e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov
534e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#if SANITIZER_INTERCEPT_CLOCK_GETTIME
535e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy StepanovINTERCEPTOR(int, clock_getres, u32 clk_id, void *tp) {
536e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  void *ctx;
537e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, clock_getres, clk_id, tp);
538e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  int res = REAL(clock_getres)(clk_id, tp);
5397cdae1683c9c2fcd4473a5862c90c64be3a8c5fdEvgeniy Stepanov  if (!res && tp) {
540e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, tp, struct_timespec_sz);
541e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  }
542e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  return res;
543e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov}
544e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy StepanovINTERCEPTOR(int, clock_gettime, u32 clk_id, void *tp) {
545e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  void *ctx;
546e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, clock_gettime, clk_id, tp);
547e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  int res = REAL(clock_gettime)(clk_id, tp);
548e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  if (!res) {
549e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, tp, struct_timespec_sz);
550e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  }
551e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  return res;
552e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov}
553e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy StepanovINTERCEPTOR(int, clock_settime, u32 clk_id, const void *tp) {
554e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  void *ctx;
555e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, clock_settime, clk_id, tp);
556e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_READ_RANGE(ctx, tp, struct_timespec_sz);
557e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  return REAL(clock_settime)(clk_id, tp);
558e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov}
559e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#define INIT_CLOCK_GETTIME                         \
560e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  INTERCEPT_FUNCTION(clock_getres);                \
561e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  INTERCEPT_FUNCTION(clock_gettime);               \
562e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  INTERCEPT_FUNCTION(clock_settime);
563e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#else
564e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#define INIT_CLOCK_GETTIME
565e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#endif
566e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov
567e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov
568e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#if SANITIZER_INTERCEPT_GETITIMER
569e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy StepanovINTERCEPTOR(int, getitimer, int which, void *curr_value) {
570e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  void *ctx;
571e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, getitimer, which, curr_value);
572e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  int res = REAL(getitimer)(which, curr_value);
573e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  if (!res) {
574e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, curr_value, struct_itimerval_sz);
575e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  }
576e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  return res;
577e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov}
578e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy StepanovINTERCEPTOR(int, setitimer, int which, const void *new_value, void *old_value) {
579e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  void *ctx;
580e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, setitimer, which, new_value, old_value);
581e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  COMMON_INTERCEPTOR_READ_RANGE(ctx, new_value, struct_itimerval_sz);
582e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  int res = REAL(setitimer)(which, new_value, old_value);
583e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  if (!res && old_value) {
584e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, old_value, struct_itimerval_sz);
585e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  }
586e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  return res;
587e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov}
588e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#define INIT_GETITIMER                             \
589e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  INTERCEPT_FUNCTION(getitimer);                   \
590e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov  INTERCEPT_FUNCTION(setitimer);
591e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#else
592e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#define INIT_GETITIMER
593e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov#endif
594e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov
595e4bdda51b3469aa0f6ef6f6c4656419effa48038Evgeniy Stepanov
596a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov#if SANITIZER_INTERCEPT_GLOB
597a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanovstruct sanitizer_glob_t {
598a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  SIZE_T gl_pathc;
599a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  char **gl_pathv;
600a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov};
601a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov
602a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanovstatic void unpoison_glob_t(void *ctx, sanitizer_glob_t *pglob) {
603a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  COMMON_INTERCEPTOR_WRITE_RANGE(ctx, pglob, sizeof(*pglob));
604a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  // +1 for NULL pointer at the end.
605a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  COMMON_INTERCEPTOR_WRITE_RANGE(
606a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov      ctx, pglob->gl_pathv, (pglob->gl_pathc + 1) * sizeof(*pglob->gl_pathv));
607a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  for (SIZE_T i = 0; i < pglob->gl_pathc; ++i) {
608a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov    char *p = pglob->gl_pathv[i];
609a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, p, REAL(strlen)(p) + 1);
610a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  }
611a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov}
612a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov
613a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy StepanovINTERCEPTOR(int, glob, const char *pattern, int flags,
614a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov            int (*errfunc)(const char *epath, int eerrno),
615a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov            sanitizer_glob_t *pglob) {
616a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  void *ctx;
617a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, glob, pattern, flags, errfunc, pglob);
618a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  int res = REAL(glob)(pattern, flags, errfunc, pglob);
619a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  if (res == 0)
620a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov    unpoison_glob_t(ctx, pglob);
621a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  return res;
622a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov}
623a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov
624a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy StepanovINTERCEPTOR(int, glob64, const char *pattern, int flags,
625a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov            int (*errfunc)(const char *epath, int eerrno),
626a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov            sanitizer_glob_t *pglob) {
627a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  void *ctx;
628a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, glob64, pattern, flags, errfunc, pglob);
629a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  int res = REAL(glob64)(pattern, flags, errfunc, pglob);
630a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  if (res == 0)
631a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov    unpoison_glob_t(ctx, pglob);
632a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  return res;
633a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov}
634a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov#define INIT_GLOB                               \
635a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  INTERCEPT_FUNCTION(glob);                     \
636a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov  INTERCEPT_FUNCTION(glob64);
637a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov#else // SANITIZER_INTERCEPT_GLOB
638a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov#define INIT_GLOB
639a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov#endif // SANITIZER_INTERCEPT_GLOB
640a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov
641a1c2a5547d815a4ce116f04ebd3cef1716ab791cEvgeniy Stepanov
642897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov#if SANITIZER_INTERCEPT_WAIT
6436a659dfd8e717a598f54867aa36c2e4af09d031bAlexander Potapenko// According to sys/wait.h, wait(), waitid(), waitpid() may have symbol version
6446a659dfd8e717a598f54867aa36c2e4af09d031bAlexander Potapenko// suffixes on Darwin. See the declaration of INTERCEPTOR_WITH_SUFFIX for
6456a659dfd8e717a598f54867aa36c2e4af09d031bAlexander Potapenko// details.
6466a659dfd8e717a598f54867aa36c2e4af09d031bAlexander PotapenkoINTERCEPTOR_WITH_SUFFIX(int, wait, int *status) {
647897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  void *ctx;
648897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, wait, status);
649897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  int res = REAL(wait)(status);
650f82eb24b61f8c0f23396ed5ba68f5ace7656e986Dmitry Vyukov  if (res != -1 && status)
651897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, status, sizeof(*status));
652897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  return res;
653897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov}
65430e970f769ccf11e61e472c6f8b22f8e866c592fKostya SerebryanyINTERCEPTOR_WITH_SUFFIX(int, waitid, int idtype, int id, void *infop,
65530e970f769ccf11e61e472c6f8b22f8e866c592fKostya Serebryany  int options) {
656897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  void *ctx;
657897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, waitid, idtype, id, infop, options);
658897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  int res = REAL(waitid)(idtype, id, infop, options);
659f82eb24b61f8c0f23396ed5ba68f5ace7656e986Dmitry Vyukov  if (res != -1 && infop)
660897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, infop, siginfo_t_sz);
661897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  return res;
662897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov}
6636a659dfd8e717a598f54867aa36c2e4af09d031bAlexander PotapenkoINTERCEPTOR_WITH_SUFFIX(int, waitpid, int pid, int *status, int options) {
664897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  void *ctx;
665897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, waitpid, pid, status, options);
666897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  int res = REAL(waitpid)(pid, status, options);
667f82eb24b61f8c0f23396ed5ba68f5ace7656e986Dmitry Vyukov  if (res != -1 && status)
668897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, status, sizeof(*status));
669897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  return res;
670897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov}
671897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy StepanovINTERCEPTOR(int, wait3, int *status, int options, void *rusage) {
672897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  void *ctx;
673897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, wait3, status, options, rusage);
674897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  int res = REAL(wait3)(status, options, rusage);
675897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  if (res != -1) {
676f82eb24b61f8c0f23396ed5ba68f5ace7656e986Dmitry Vyukov    if (status)
677f82eb24b61f8c0f23396ed5ba68f5ace7656e986Dmitry Vyukov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, status, sizeof(*status));
678897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov    if (rusage)
679897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, rusage, struct_rusage_sz);
680897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  }
681897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  return res;
682897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov}
683897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy StepanovINTERCEPTOR(int, wait4, int pid, int *status, int options, void *rusage) {
684897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  void *ctx;
685897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, wait4, pid, status, options, rusage);
686897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  int res = REAL(wait4)(pid, status, options, rusage);
687897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  if (res != -1) {
688f82eb24b61f8c0f23396ed5ba68f5ace7656e986Dmitry Vyukov    if (status)
689f82eb24b61f8c0f23396ed5ba68f5ace7656e986Dmitry Vyukov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, status, sizeof(*status));
690897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov    if (rusage)
691897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, rusage, struct_rusage_sz);
692897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  }
693897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  return res;
694897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov}
695897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov#define INIT_WAIT                                \
696897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  INTERCEPT_FUNCTION(wait);                      \
697897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  INTERCEPT_FUNCTION(waitid);                    \
698897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  INTERCEPT_FUNCTION(waitpid);                   \
699897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  INTERCEPT_FUNCTION(wait3);                     \
700897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov  INTERCEPT_FUNCTION(wait4);
701897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov#else
702897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov#define INIT_WAIT
703897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov#endif
704897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov
7059530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov#if SANITIZER_INTERCEPT_INET
7069530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy StepanovINTERCEPTOR(char *, inet_ntop, int af, const void *src, char *dst, u32 size) {
7079530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  void *ctx;
7089530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, inet_ntop, af, src, dst, size);
7099530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  uptr sz = __sanitizer_in_addr_sz(af);
7109530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  if (sz) COMMON_INTERCEPTOR_READ_RANGE(ctx, src, sz);
7119530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  // FIXME: figure out read size based on the address family.
7129530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  char *res = REAL(inet_ntop)(af, src, dst, size);
7139530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  if (res)
7149530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, res, REAL(strlen)(res) + 1);
7159530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  return res;
7169530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov}
7179530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy StepanovINTERCEPTOR(int, inet_pton, int af, const char *src, void *dst) {
7189530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  void *ctx;
7199530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, inet_pton, af, src, dst);
7209530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  // FIXME: figure out read size based on the address family.
7219530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  int res = REAL(inet_pton)(af, src, dst);
7229530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  if (res == 1) {
7239530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov    uptr sz = __sanitizer_in_addr_sz(af);
7249530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov    if (sz) COMMON_INTERCEPTOR_WRITE_RANGE(ctx, dst, sz);
7259530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  }
7269530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  return res;
7279530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov}
7289530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov#define INIT_INET                                \
7299530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  INTERCEPT_FUNCTION(inet_ntop);                 \
7309530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov  INTERCEPT_FUNCTION(inet_pton);
7319530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov#else
7329530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov#define INIT_INET
7339530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov#endif
7349530eb721dfacdf2c3f46d408e22d3f7cf8be667Evgeniy Stepanov
73556d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov#if SANITIZER_INTERCEPT_PTHREAD_GETSCHEDPARAM
73656d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy StepanovINTERCEPTOR(int, pthread_getschedparam, uptr thread, int *policy, int *param) {
73756d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  void *ctx;
73856d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, pthread_getschedparam, thread, policy, param);
73956d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  int res = REAL(pthread_getschedparam)(thread, policy, param);
74056d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  if (res == 0) {
74156d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov    if (policy) COMMON_INTERCEPTOR_WRITE_RANGE(ctx, policy, sizeof(*policy));
74256d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov    if (param) COMMON_INTERCEPTOR_WRITE_RANGE(ctx, param, sizeof(*param));
74356d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  }
74456d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  return res;
74556d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov}
74656d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov#define INIT_PTHREAD_GETSCHEDPARAM INTERCEPT_FUNCTION(pthread_getschedparam);
74756d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov#else
74856d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov#define INIT_PTHREAD_GETSCHEDPARAM
74956d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov#endif
750897a4ae31f5c55255c78854b69b4cd4a4e3c7c39Evgeniy Stepanov
751447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov#if SANITIZER_INTERCEPT_GETADDRINFO
752447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy StepanovINTERCEPTOR(int, getaddrinfo, char *node, char *service,
753447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov            struct __sanitizer_addrinfo *hints,
754447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov            struct __sanitizer_addrinfo **out) {
755447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov  void *ctx;
756447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, getaddrinfo, node, service, hints, out);
757447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov  if (node) COMMON_INTERCEPTOR_READ_RANGE(ctx, node, REAL(strlen)(node) + 1);
758447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov  if (service)
759447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, service, REAL(strlen)(service) + 1);
760447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov  if (hints)
761447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov    COMMON_INTERCEPTOR_READ_RANGE(ctx, hints, sizeof(__sanitizer_addrinfo));
762447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov  int res = REAL(getaddrinfo)(node, service, hints, out);
763447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov  if (res == 0) {
764447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov    struct __sanitizer_addrinfo *p = *out;
765447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov    while (p) {
766447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, p, sizeof(__sanitizer_addrinfo));
767447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov      if (p->ai_addr)
768447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov        COMMON_INTERCEPTOR_WRITE_RANGE(ctx, p->ai_addr, struct_sockaddr_sz);
769447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov      if (p->ai_canonname)
770447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov        COMMON_INTERCEPTOR_WRITE_RANGE(ctx, p->ai_canonname,
771447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov                                       REAL(strlen)(p->ai_canonname) + 1);
772447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov      p = p->ai_next;
773447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov    }
774447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov  }
775447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov  return res;
776447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov}
777447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov#define INIT_GETADDRINFO INTERCEPT_FUNCTION(getaddrinfo);
778447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov#else
779447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov#define INIT_GETADDRINFO
780447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov#endif
781447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov
7829f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov#if SANITIZER_INTERCEPT_GETSOCKNAME
7839f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy StepanovINTERCEPTOR(int, getsockname, int sock_fd, void *addr, int *addrlen) {
7849f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov  void *ctx;
7859f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, getsockname, sock_fd, addr, addrlen);
7869f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov  COMMON_INTERCEPTOR_READ_RANGE(ctx, addrlen, sizeof(*addrlen));
7879f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov  int addrlen_in = *addrlen;
7889f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov  int res = REAL(getsockname)(sock_fd, addr, addrlen);
7899f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov  if (res == 0) {
7909f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, addr, Min(addrlen_in, *addrlen));
7919f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov  }
7929f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov  return res;
7939f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov}
7949f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov#define INIT_GETSOCKNAME INTERCEPT_FUNCTION(getsockname);
7959f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov#else
7969f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov#define INIT_GETSOCKNAME
7979f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov#endif
798447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov
7990a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanovstatic void write_hostent(void *ctx, struct __sanitizer_hostent *h) {
8000a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_WRITE_RANGE(ctx, h, sizeof(__sanitizer_hostent));
8010a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  if (h->h_name)
8020a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, h->h_name, REAL(strlen)(h->h_name) + 1);
8030a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  char **p = h->h_aliases;
8040a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  while (*p) {
8050a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, *p, REAL(strlen)(*p) + 1);
8060a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    ++p;
8070a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  }
8080a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_WRITE_RANGE(
8090a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      ctx, h->h_aliases, (p - h->h_aliases + 1) * sizeof(*h->h_aliases));
8100a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  p = h->h_addr_list;
8110a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  while (*p) {
8120a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, *p, h->h_length);
8130a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    ++p;
8140a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  }
8150a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_WRITE_RANGE(
8160a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      ctx, h->h_addr_list, (p - h->h_addr_list + 1) * sizeof(*h->h_addr_list));
8170a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov}
8180a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov
8190a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov#if SANITIZER_INTERCEPT_GETHOSTBYNAME
8200a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy StepanovINTERCEPTOR(struct __sanitizer_hostent *, gethostbyname, char *name) {
8210a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  void *ctx;
8220a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, gethostbyname, name);
8230a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  struct __sanitizer_hostent *res = REAL(gethostbyname)(name);
8240a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  if (res) write_hostent(ctx, res);
8250a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  return res;
8260a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov}
8270a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov
8280a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy StepanovINTERCEPTOR(struct __sanitizer_hostent *, gethostbyaddr, void *addr, int len,
8290a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov            int type) {
8300a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  void *ctx;
8310a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, gethostbyaddr, addr, len, type);
8320a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_READ_RANGE(ctx, addr, len);
8330a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  struct __sanitizer_hostent *res = REAL(gethostbyaddr)(addr, len, type);
8340a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  if (res) write_hostent(ctx, res);
8350a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  return res;
8360a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov}
8370a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov
8380a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy StepanovINTERCEPTOR(struct __sanitizer_hostent *, gethostent) {
8390a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  void *ctx;
8400a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, gethostent);
8410a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  struct __sanitizer_hostent *res = REAL(gethostent)();
8420a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  if (res) write_hostent(ctx, res);
8430a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  return res;
8440a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov}
8450a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov
8460a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy StepanovINTERCEPTOR(struct __sanitizer_hostent *, gethostbyname2, char *name, int af) {
8470a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  void *ctx;
8480a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, gethostbyname2, name, af);
8490a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  struct __sanitizer_hostent *res = REAL(gethostbyname2)(name, af);
8500a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  if (res) write_hostent(ctx, res);
8510a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  return res;
8520a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov}
8530a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov#define INIT_GETHOSTBYNAME           \
8540a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  INTERCEPT_FUNCTION(gethostent);    \
8550a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  INTERCEPT_FUNCTION(gethostbyaddr); \
8560a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  INTERCEPT_FUNCTION(gethostbyname); \
8570a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  INTERCEPT_FUNCTION(gethostbyname2);
8580a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov#else
8590a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov#define INIT_GETHOSTBYNAME
8600a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov#endif
8610a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov
8620a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov#if SANITIZER_INTERCEPT_GETHOSTBYNAME_R
8630a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy StepanovINTERCEPTOR(int, gethostent_r, struct __sanitizer_hostent *ret, char *buf,
8640a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov            SIZE_T buflen, __sanitizer_hostent **result, int *h_errnop) {
8650a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  void *ctx;
8660a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, gethostent_r, ret, buf, buflen, result,
8670a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov                           h_errnop);
8680a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  int res = REAL(gethostent_r)(ret, buf, buflen, result, h_errnop);
8690a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  if (res == 0) {
8700a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    if (result) {
8710a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, result, sizeof(*result));
8720a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      if (*result) write_hostent(ctx, *result);
8730a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    }
8740a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    if (h_errnop)
8750a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, h_errnop, sizeof(*h_errnop));
8760a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  }
8770a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  return res;
8780a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov}
8790a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov
8800a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy StepanovINTERCEPTOR(int, gethostbyaddr_r, void *addr, int len, int type,
8810a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov            struct __sanitizer_hostent *ret, char *buf, SIZE_T buflen,
8820a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov            __sanitizer_hostent **result, int *h_errnop) {
8830a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  void *ctx;
8840a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, gethostbyaddr_r, addr, len, type, ret, buf,
8850a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov                           buflen, result, h_errnop);
8860a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_READ_RANGE(ctx, addr, len);
8870a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  int res = REAL(gethostbyaddr_r)(addr, len, type, ret, buf, buflen, result,
8880a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov                                  h_errnop);
8890a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  if (res == 0) {
8900a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    if (result) {
8910a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, result, sizeof(*result));
8920a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      if (*result) write_hostent(ctx, *result);
8930a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    }
8940a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    if (h_errnop)
8950a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, h_errnop, sizeof(*h_errnop));
8960a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  }
8970a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  return res;
8980a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov}
8990a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov
9000a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy StepanovINTERCEPTOR(int, gethostbyname_r, char *name, struct __sanitizer_hostent *ret,
9010a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov            char *buf, SIZE_T buflen, __sanitizer_hostent **result,
9020a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov            int *h_errnop) {
9030a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  void *ctx;
9040a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, gethostbyname_r, name, ret, buf, buflen, result,
9050a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov                           h_errnop);
9060a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  int res = REAL(gethostbyname_r)(name, ret, buf, buflen, result, h_errnop);
9070a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  if (res == 0) {
9080a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    if (result) {
9090a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, result, sizeof(*result));
9100a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      if (*result) write_hostent(ctx, *result);
9110a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    }
9120a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    if (h_errnop)
9130a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, h_errnop, sizeof(*h_errnop));
9140a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  }
9150a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  return res;
9160a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov}
9170a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov
9180a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy StepanovINTERCEPTOR(int, gethostbyname2_r, char *name, int af,
9190a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov            struct __sanitizer_hostent *ret, char *buf, SIZE_T buflen,
9200a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov            __sanitizer_hostent **result, int *h_errnop) {
9210a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  void *ctx;
9220a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  COMMON_INTERCEPTOR_ENTER(ctx, gethostbyname2_r, name, af, ret, buf, buflen,
9230a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov                           result, h_errnop);
9240a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  int res =
9250a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      REAL(gethostbyname2_r)(name, af, ret, buf, buflen, result, h_errnop);
9260a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  if (res == 0) {
9270a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    if (result) {
9280a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, result, sizeof(*result));
9290a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      if (*result) write_hostent(ctx, *result);
9300a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    }
9310a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov    if (h_errnop)
9320a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov      COMMON_INTERCEPTOR_WRITE_RANGE(ctx, h_errnop, sizeof(*h_errnop));
9330a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  }
9340a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  return res;
9350a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov}
9360a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov#define INIT_GETHOSTBYNAME_R           \
9370a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  INTERCEPT_FUNCTION(gethostent_r);    \
9380a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  INTERCEPT_FUNCTION(gethostbyaddr_r); \
9390a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  INTERCEPT_FUNCTION(gethostbyname_r); \
9400a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  INTERCEPT_FUNCTION(gethostbyname2_r);
9410a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov#else
9420a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov#define INIT_GETHOSTBYNAME_R
9430a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov#endif
9440a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov
94556d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov#define SANITIZER_COMMON_INTERCEPTORS_INIT \
94656d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_STRCASECMP;                         \
94756d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_STRNCASECMP;                        \
94856d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_READ;                               \
94956d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_PREAD;                              \
95056d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_PREAD64;                            \
95156d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_PRCTL;                              \
95256d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_WRITE;                              \
95356d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_PWRITE;                             \
95456d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_PWRITE64;                           \
95556d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_LOCALTIME_AND_FRIENDS;              \
95656d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_SCANF;                              \
95756d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_FREXP;                              \
95856d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_FREXPF_FREXPL;                      \
95956d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_GETPWNAM_AND_FRIENDS;               \
96056d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_GETPWNAM_R_AND_FRIENDS;             \
96156d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_CLOCK_GETTIME;                      \
96256d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_GETITIMER;                          \
96356d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_TIME;                               \
96456d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_GLOB;                               \
96556d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_WAIT;                               \
96656d3472104dd9fec6578e02f4895f3254e038e8eEvgeniy Stepanov  INIT_INET;                               \
967447ef19d1b8cebbeaba49e4be22ac721448dcf3eEvgeniy Stepanov  INIT_PTHREAD_GETSCHEDPARAM;              \
9689f58c5c60a56d9c39d36b5313dc87ad4bb713163Evgeniy Stepanov  INIT_GETADDRINFO;                        \
9690a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  INIT_GETSOCKNAME;                        \
9700a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  INIT_GETHOSTBYNAME;                      \
9710a2cc37712a452525f9f03b3bf67b1f0a97c8d3aEvgeniy Stepanov  INIT_GETHOSTBYNAME_R;
972