brintos

brintos / llvm-project-archived public Read only

0
0
Text · 64.7 KiB · 873af5c Raw
2371 lines · cpp
1// RUN: %clang_dfsan %s -o %t && env DFSAN_OPTIONS="strict_data_dependencies=0" %run %t2// RUN: %clang_dfsan -DSTRICT_DATA_DEPENDENCIES %s -o %t && %run %t3// RUN: %clang_dfsan -DORIGIN_TRACKING -mllvm -dfsan-track-origins=1 -mllvm -dfsan-combine-pointer-labels-on-load=false -DSTRICT_DATA_DEPENDENCIES %s -o %t && %run %t4// RUN: %clang_dfsan -DORIGIN_TRACKING -mllvm -dfsan-track-origins=1 -mllvm -dfsan-combine-pointer-labels-on-load=false -no-pie %s -o %t && env DFSAN_OPTIONS="strict_data_dependencies=0" %run %t5//6// Tests custom implementations of various glibc functions.7 8#pragma clang diagnostic ignored "-Wformat-extra-args"9 10#include <sanitizer/dfsan_interface.h>11 12#include <arpa/inet.h>13#include <assert.h>14#include <fcntl.h>15#include <link.h>16#include <poll.h>17#include <pthread.h>18#include <pwd.h>19#include <sched.h>20#include <signal.h>21#include <stdint.h>22#include <stdio.h>23#include <stdlib.h>24#include <string.h>25#include <strings.h>26#include <sys/epoll.h>27#include <sys/resource.h>28#include <sys/select.h>29#include <sys/socket.h>30#include <sys/stat.h>31#include <sys/time.h>32#include <sys/types.h>33#include <time.h>34#include <unistd.h>35 36dfsan_label i_label = 0;37dfsan_label j_label = 0;38dfsan_label k_label = 0;39dfsan_label m_label = 0;40dfsan_label n_label = 0;41dfsan_label i_j_label = 0;42 43#define ASSERT_ZERO_LABEL(data) \44  assert(0 == dfsan_get_label((long) (data)))45 46#define ASSERT_READ_ZERO_LABEL(ptr, size) \47  assert(0 == dfsan_read_label(ptr, size))48 49#define ASSERT_LABEL(data, label) \50  assert(label == dfsan_get_label((long) (data)))51 52#define ASSERT_READ_LABEL(ptr, size, label) \53  assert(label == dfsan_read_label(ptr, size))54 55#ifdef ORIGIN_TRACKING56#define ASSERT_ZERO_ORIGIN(data) \57  assert(0 == dfsan_get_origin((long)(data)))58#else59#define ASSERT_ZERO_ORIGIN(data)60#endif61 62#ifdef ORIGIN_TRACKING63#define ASSERT_ZERO_ORIGINS(ptr, size)                       \64  for (int i = 0; i < size; ++i) {                           \65    assert(0 == dfsan_get_origin((long)(((char *)ptr)[i]))); \66  }67#else68#define ASSERT_ZERO_ORIGINS(ptr, size)69#endif70 71#ifdef ORIGIN_TRACKING72#define ASSERT_ORIGIN(data, origin) \73  assert(origin == dfsan_get_origin((long)(data)))74#else75#define ASSERT_ORIGIN(data, origin)76#endif77 78#ifdef ORIGIN_TRACKING79#define ASSERT_ORIGINS(ptr, size, origin)                         \80  for (int i = 0; i < size; ++i) {                                \81    assert(origin == dfsan_get_origin((long)(((char *)ptr)[i]))); \82  }83#else84#define ASSERT_ORIGINS(ptr, size, origin)85#endif86 87#ifdef ORIGIN_TRACKING88#define ASSERT_INIT_ORIGIN(ptr, origin) \89  assert(origin == dfsan_get_init_origin(ptr))90#else91#define ASSERT_INIT_ORIGIN(ptr, origin)92#endif93 94#ifdef ORIGIN_TRACKING95#define ASSERT_INIT_ORIGIN_EQ_ORIGIN(ptr, data) \96  assert(dfsan_get_origin((long)(data)) == dfsan_get_init_origin(ptr))97#else98#define ASSERT_INIT_ORIGIN_EQ_ORIGIN(ptr, data)99#endif100 101#ifdef ORIGIN_TRACKING102#define ASSERT_INIT_ORIGINS(ptr, size, origin)                  \103  for (int i = 0; i < size; ++i) {                              \104    assert(origin == dfsan_get_init_origin(&((char *)ptr)[i])); \105  }106#else107#define ASSERT_INIT_ORIGINS(ptr, size, origin)108#endif109 110#ifdef ORIGIN_TRACKING111#define ASSERT_EQ_ORIGIN(data1, data2) \112  assert(dfsan_get_origin((long)(data1)) == dfsan_get_origin((long)(data2)))113#else114#define ASSERT_EQ_ORIGIN(data1, data2)115#endif116 117#ifdef ORIGIN_TRACKING118#define DEFINE_AND_SAVE_ORIGINS(val)    \119  dfsan_origin val##_o[sizeof(val)];    \120  for (int i = 0; i < sizeof(val); ++i) \121    val##_o[i] = dfsan_get_origin((long)(((char *)(&val))[i]));122#else123#define DEFINE_AND_SAVE_ORIGINS(val)124#endif125 126#ifdef ORIGIN_TRACKING127#define SAVE_ORIGINS(val)               \128  for (int i = 0; i < sizeof(val); ++i) \129    val##_o[i] = dfsan_get_origin((long)(((char *)(&val))[i]));130#else131#define SAVE_ORIGINS(val)132#endif133 134#ifdef ORIGIN_TRACKING135#define ASSERT_SAVED_ORIGINS(val)       \136  for (int i = 0; i < sizeof(val); ++i) \137    ASSERT_ORIGIN(((char *)(&val))[i], val##_o[i]);138#else139#define ASSERT_SAVED_ORIGINS(val)140#endif141 142#ifdef ORIGIN_TRACKING143#define DEFINE_AND_SAVE_N_ORIGINS(val, n) \144  dfsan_origin val##_o[n];                \145  for (int i = 0; i < n; ++i)             \146    val##_o[i] = dfsan_get_origin((long)(val[i]));147#else148#define DEFINE_AND_SAVE_N_ORIGINS(val, n)149#endif150 151#ifdef ORIGIN_TRACKING152#define ASSERT_SAVED_N_ORIGINS(val, n) \153  for (int i = 0; i < n; ++i)          \154    ASSERT_ORIGIN(val[i], val##_o[i]);155#else156#define ASSERT_SAVED_N_ORIGINS(val, n)157#endif158 159#if !defined(__GLIBC_PREREQ)160#  define __GLIBC_PREREQ(a, b) 0161#endif162 163void test_stat() {164  int i = 1;165  dfsan_set_label(i_label, &i, sizeof(i));166 167  struct stat s;168  s.st_dev = i;169  DEFINE_AND_SAVE_ORIGINS(s)170  int ret = stat("/", &s);171  assert(0 == ret);172  ASSERT_ZERO_LABEL(ret);173  ASSERT_ZERO_LABEL(s.st_dev);174  ASSERT_SAVED_ORIGINS(s)175 176  s.st_dev = i;177  SAVE_ORIGINS(s)178  ret = stat("/nonexistent_581cb021aba7", &s);179  assert(-1 == ret);180  ASSERT_ZERO_LABEL(ret);181  ASSERT_LABEL(s.st_dev, i_label);182  ASSERT_SAVED_ORIGINS(s)183}184 185void test_fstat() {186  int i = 1;187  dfsan_set_label(i_label, &i, sizeof(i));188 189  struct stat s;190  int fd = open("/dev/zero", O_RDONLY);191  s.st_dev = i;192  DEFINE_AND_SAVE_ORIGINS(s)193  int rv = fstat(fd, &s);194  assert(0 == rv);195  ASSERT_ZERO_LABEL(rv);196  ASSERT_ZERO_LABEL(s.st_dev);197  ASSERT_SAVED_ORIGINS(s)198}199 200void test_memcmp() {201  char str1[] = "str1", str2[] = "str2";202  dfsan_set_label(i_label, &str1[3], 1);203  dfsan_set_label(j_label, &str2[3], 1);204 205  int rv = memcmp(str1, str2, sizeof(str1));206  assert(rv < 0);207#ifdef STRICT_DATA_DEPENDENCIES208  ASSERT_ZERO_LABEL(rv);209#else210  ASSERT_LABEL(rv, i_j_label);211  ASSERT_EQ_ORIGIN(rv, str1[3]);212#endif213 214  rv = memcmp(str1, str2, sizeof(str1) - 2);215  assert(rv == 0);216  ASSERT_ZERO_LABEL(rv);217}218 219void test_bcmp() {220  char str1[] = "str1", str2[] = "str2";221  dfsan_set_label(i_label, &str1[3], 1);222  dfsan_set_label(j_label, &str2[3], 1);223 224  int rv = bcmp(str1, str2, sizeof(str1));225  assert(rv != 0);226#ifdef STRICT_DATA_DEPENDENCIES227  ASSERT_ZERO_LABEL(rv);228#else229  ASSERT_LABEL(rv, i_j_label);230  ASSERT_EQ_ORIGIN(rv, str1[3]);231#endif232 233  rv = bcmp(str1, str2, sizeof(str1) - 2);234  assert(rv == 0);235  ASSERT_ZERO_LABEL(rv);236}237 238void test_memcpy() {239  char str1[] = "str1";240  char str2[sizeof(str1)];241  dfsan_set_label(i_label, &str1[3], 1);242 243  DEFINE_AND_SAVE_ORIGINS(str1)244 245  char *ptr2 = str2;246  dfsan_set_label(j_label, &ptr2, sizeof(ptr2));247 248  void *r = memcpy(ptr2, str1, sizeof(str1));249  ASSERT_LABEL(r, j_label);250  ASSERT_EQ_ORIGIN(r, ptr2);251  assert(0 == memcmp(str2, str1, sizeof(str1)));252  ASSERT_ZERO_LABEL(str2[0]);253  ASSERT_LABEL(str2[3], i_label);254 255  for (int i = 0; i < sizeof(str2); ++i) {256    if (!dfsan_get_label(str2[i]))257      continue;258    ASSERT_INIT_ORIGIN(&(str2[i]), str1_o[i]);259  }260}261 262void test_memmove() {263  char str[] = "str1xx";264  dfsan_set_label(i_label, &str[3], 1);265 266  DEFINE_AND_SAVE_ORIGINS(str)267 268  char *ptr = str + 2;269  dfsan_set_label(j_label, &ptr, sizeof(ptr));270 271  void *r = memmove(ptr, str, 4);272  ASSERT_LABEL(r, j_label);273  ASSERT_EQ_ORIGIN(r, ptr);274  assert(0 == memcmp(str + 2, "str1", 4));275  ASSERT_ZERO_LABEL(str[4]);276  ASSERT_LABEL(str[5], i_label);277 278  for (int i = 0; i < 4; ++i) {279    if (!dfsan_get_label(ptr[i]))280      continue;281    ASSERT_INIT_ORIGIN(&(ptr[i]), str_o[i]);282  }283}284 285void test_memset() {286  char buf[8];287  int j = 'a';288  char *ptr = buf;289  dfsan_set_label(j_label, &j, sizeof(j));290  dfsan_set_label(k_label, &ptr, sizeof(ptr));291  void *ret = memset(ptr, j, sizeof(buf));292  ASSERT_LABEL(ret, k_label);293  ASSERT_EQ_ORIGIN(ret, ptr);294  for (int i = 0; i < 8; ++i) {295    ASSERT_LABEL(buf[i], j_label);296    ASSERT_EQ_ORIGIN(buf[i], j);297    assert(buf[i] == 'a');298  }299}300 301void test_strcmp() {302  char str1[] = "str1", str2[] = "str2";303  dfsan_set_label(i_label, &str1[3], 1);304  dfsan_set_label(j_label, &str2[3], 1);305 306  int rv = strcmp(str1, str2);307  assert(rv < 0);308#ifdef STRICT_DATA_DEPENDENCIES309  ASSERT_ZERO_LABEL(rv);310#else311  ASSERT_LABEL(rv, i_j_label);312  ASSERT_EQ_ORIGIN(rv, str1[3]);313#endif314 315  rv = strcmp(str1, str1);316  assert(rv == 0);317#ifdef STRICT_DATA_DEPENDENCIES318  ASSERT_ZERO_LABEL(rv);319  ASSERT_ZERO_ORIGIN(rv);320#else321  ASSERT_LABEL(rv, i_label);322  ASSERT_EQ_ORIGIN(rv, str1[3]);323#endif324}325 326void test_strcat() {327  char src[] = "world";328  int volatile x = 0; // buffer to ensure src and dst do not share origins329  (void)x;330  char dst[] = "hello \0    ";331  int volatile y = 0; // buffer to ensure dst and p do not share origins332  (void)y;333  char *p = dst;334  dfsan_set_label(k_label, &p, sizeof(p));335  dfsan_set_label(i_label, src, sizeof(src));336  dfsan_set_label(j_label, dst, sizeof(dst));337  dfsan_origin dst_o = dfsan_get_origin((long)dst[0]);338  (void)dst_o;339  char *ret = strcat(p, src);340 341  ASSERT_LABEL(ret, k_label);342  ASSERT_EQ_ORIGIN(ret, p);343  assert(ret == dst);344  assert(strcmp(src, dst + 6) == 0);345  // Origins are assigned for every 4 contiguous 4-aligned bytes. After346  // appending src to dst, origins of src can overwrite origins of dst if their347  // application adddresses are within [start_aligned_down, end_aligned_up).348  // Other origins are not changed.349  char *start_aligned_down = (char *)(((size_t)(dst + 6)) & ~3UL);350  char *end_aligned_up = (char *)(((size_t)(dst + 11 + 4)) & ~3UL);351  for (int i = 0; i < 12; ++i) {352    if (dst + i < start_aligned_down || dst + i >= end_aligned_up) {353      ASSERT_INIT_ORIGIN(&dst[i], dst_o);354    } else {355      ASSERT_INIT_ORIGIN_EQ_ORIGIN(&dst[i], src[0]);356    }357  }358  for (int i = 0; i < 6; ++i) {359    ASSERT_LABEL(dst[i], j_label);360  }361  for (int i = 6; i < strlen(dst); ++i) {362    ASSERT_LABEL(dst[i], i_label);363    assert(dfsan_get_label(dst[i]) == dfsan_get_label(src[i - 6]));364  }365  ASSERT_LABEL(dst[11], j_label);366}367 368void test_strncat(int n) {369  char src[] = "world";370  int volatile x = 0; // buffer to ensure src and dst do not share origins371  (void)x;372  char dst[] = "hello \0    ";373  int volatile y = 0; // buffer to ensure dst and p do not share origins374  (void)y;375  char *p = dst;376  dfsan_set_label(k_label, &p, sizeof(p));377  dfsan_set_label(i_label, src, sizeof(src));378  dfsan_set_label(j_label, dst, sizeof(dst));379  dfsan_origin dst_o = dfsan_get_origin((long)dst[0]);380  (void)dst_o;381  char *ret = strncat(p, src, n);382 383  ASSERT_LABEL(ret, k_label);384  ASSERT_EQ_ORIGIN(ret, p);385  assert(ret == dst);386  assert(strncmp(src, dst + 6, n) == 0);387  // Origins are assigned for every 4 contiguous 4-aligned bytes. After388  // appending src to dst, origins of src can overwrite origins of dst if their389  // application adddresses are within [start_aligned_down, end_aligned_up).390  // Other origins are not changed.391  int pad = n % 4;392  if (pad)393    pad = 4 - pad;394 395  char *start_aligned_down = (char *)(((size_t)(dst + 6)) & ~3UL);396  char *end_aligned_up = (char *)(((size_t)(dst + 6 + n + pad)) & ~3UL);397 398  for (int i = 0; i < 12; ++i) {399    if (dst + i < start_aligned_down || dst + i >= end_aligned_up) {400      ASSERT_INIT_ORIGIN(&dst[i], dst_o);401    } else {402      ASSERT_INIT_ORIGIN_EQ_ORIGIN(&dst[i], src[0]);403    }404  }405  for (int i = 0; i < 6; ++i) {406    ASSERT_LABEL(dst[i], j_label);407  }408  for (int i = 6; i < 6 + n; ++i) {409    ASSERT_LABEL(dst[i], i_label);410    assert(dfsan_get_label(dst[i]) == dfsan_get_label(src[i - 6]));411  }412  for (int i = 6 + n; i < strlen(dst); ++i) {413    ASSERT_LABEL(dst[i], j_label);414  }415  ASSERT_LABEL(dst[11], j_label);416}417 418void test_strlen() {419  char str1[] = "str1";420  dfsan_set_label(i_label, &str1[3], 1);421 422  int rv = strlen(str1);423  assert(rv == 4);424#ifdef STRICT_DATA_DEPENDENCIES425  ASSERT_ZERO_LABEL(rv);426#else427  ASSERT_LABEL(rv, i_label);428  ASSERT_EQ_ORIGIN(rv, str1[3]);429#endif430}431 432void test_strnlen() {433  char str1[] = "str1";434  dfsan_set_label(i_label, &str1[3], 1);435 436  int maxlen = 4;437  dfsan_set_label(j_label, &maxlen, sizeof(maxlen));438 439  int rv = strnlen(str1, maxlen);440  assert(rv == 4);441#ifdef STRICT_DATA_DEPENDENCIES442  ASSERT_ZERO_LABEL(rv);443#else444  ASSERT_LABEL(rv, dfsan_union(i_label, j_label));445  ASSERT_EQ_ORIGIN(rv, str1[3]);446#endif447 448  maxlen = 2;449  dfsan_set_label(j_label, &maxlen, sizeof(maxlen));450  rv = strnlen(str1, maxlen);451  assert(rv == 2);452#ifdef STRICT_DATA_DEPENDENCIES453  ASSERT_ZERO_LABEL(rv);454#else455  ASSERT_LABEL(rv, j_label);456  ASSERT_EQ_ORIGIN(rv, maxlen);457#endif458}459 460void test_strdup() {461  char str1[] = "str1";462  dfsan_set_label(i_label, &str1[3], 1);463  DEFINE_AND_SAVE_ORIGINS(str1)464 465  char *strd = strdup(str1);466  ASSERT_ZERO_LABEL(strd);467  ASSERT_ZERO_LABEL(strd[0]);468  ASSERT_LABEL(strd[3], i_label);469 470  for (int i = 0; i < strlen(strd); ++i) {471    if (!dfsan_get_label(strd[i]))472      continue;473    ASSERT_INIT_ORIGIN(&(strd[i]), str1_o[i]);474  }475 476  free(strd);477}478 479void test_strncpy() {480  char str1[] = "str1";481  char str2[sizeof(str1)];482  dfsan_set_label(i_label, &str1[3], 1);483 484  char *strd = strncpy(str2, str1, 5);485  assert(strd == str2);486  assert(strcmp(str1, str2) == 0);487  ASSERT_ZERO_LABEL(strd);488  ASSERT_ZERO_LABEL(strd[0]);489  ASSERT_ZERO_LABEL(strd[1]);490  ASSERT_ZERO_LABEL(strd[2]);491  ASSERT_LABEL(strd[3], i_label);492  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&(strd[3]), str1[3]);493 494  char *p2 = str2;495  dfsan_set_label(j_label, &p2, sizeof(p2));496  strd = strncpy(p2, str1, 3);497  assert(strd == str2);498  assert(strncmp(str1, str2, 3) == 0);499  ASSERT_LABEL(strd, j_label);500  ASSERT_EQ_ORIGIN(strd, p2);501  // When -dfsan-combine-pointer-labels-on-load is on, strd's label propagates502  // to strd[i]'s label. When ORIGIN_TRACKING is defined,503  // -dfsan-combine-pointer-labels-on-load is always off, otherwise the flag504  // is on by default.505#if defined(ORIGIN_TRACKING)506  ASSERT_ZERO_LABEL(strd[0]);507  ASSERT_ZERO_LABEL(strd[1]);508  ASSERT_ZERO_LABEL(strd[2]);509#else510  ASSERT_LABEL(strd[0], j_label);511  ASSERT_LABEL(strd[1], j_label);512  ASSERT_LABEL(strd[2], j_label);513#endif514}515 516void test_strncmp() {517  char str1[] = "str1", str2[] = "str2";518  dfsan_set_label(i_label, &str1[3], 1);519  dfsan_set_label(j_label, &str2[3], 1);520 521  int rv = strncmp(str1, str2, sizeof(str1));522  assert(rv < 0);523#ifdef STRICT_DATA_DEPENDENCIES524  ASSERT_ZERO_LABEL(rv);525#else526  ASSERT_LABEL(rv, dfsan_union(i_label, j_label));527  ASSERT_EQ_ORIGIN(rv, str1[3]);528#endif529 530  rv = strncmp(str1, str2, 0);531  assert(rv == 0);532  ASSERT_ZERO_LABEL(rv);533 534  rv = strncmp(str1, str2, 3);535  assert(rv == 0);536  ASSERT_ZERO_LABEL(rv);537 538  rv = strncmp(str1, str1, 4);539  assert(rv == 0);540#ifdef STRICT_DATA_DEPENDENCIES541  ASSERT_ZERO_LABEL(rv);542#else543  ASSERT_LABEL(rv, i_label);544  ASSERT_EQ_ORIGIN(rv, str1[3]);545#endif546}547 548void test_strcasecmp() {549  char str1[] = "str1", str2[] = "str2", str3[] = "Str1";550  dfsan_set_label(i_label, &str1[3], 1);551  dfsan_set_label(j_label, &str2[3], 1);552  dfsan_set_label(j_label, &str3[2], 1);553 554  int rv = strcasecmp(str1, str2);555  assert(rv < 0);556#ifdef STRICT_DATA_DEPENDENCIES557  ASSERT_ZERO_LABEL(rv);558#else559  ASSERT_LABEL(rv, dfsan_union(i_label, j_label));560  ASSERT_EQ_ORIGIN(rv, str1[3]);561#endif562 563  rv = strcasecmp(str1, str3);564  assert(rv == 0);565#ifdef STRICT_DATA_DEPENDENCIES566  ASSERT_ZERO_LABEL(rv);567#else568  ASSERT_LABEL(rv, dfsan_union(i_label, j_label));569  ASSERT_EQ_ORIGIN(rv, str1[3]);570#endif571 572  char s1[] = "AbZ";573  char s2[] = "aBy";574  dfsan_set_label(i_label, &s1[2], 1);575  dfsan_set_label(j_label, &s2[2], 1);576 577  rv = strcasecmp(s1, s2);578  assert(rv > 0); // 'Z' > 'y'579#ifdef STRICT_DATA_DEPENDENCIES580  ASSERT_ZERO_LABEL(rv);581#else582  ASSERT_LABEL(rv, dfsan_union(i_label, j_label));583  ASSERT_EQ_ORIGIN(rv, s1[2]);584#endif585}586 587void test_strncasecmp() {588  char str1[] = "Str1", str2[] = "str2";589  dfsan_set_label(i_label, &str1[3], 1);590  dfsan_set_label(j_label, &str2[3], 1);591 592  int rv = strncasecmp(str1, str2, sizeof(str1));593  assert(rv < 0);594#ifdef STRICT_DATA_DEPENDENCIES595  ASSERT_ZERO_LABEL(rv);596#else597  ASSERT_LABEL(rv, dfsan_union(i_label, j_label));598  ASSERT_EQ_ORIGIN(rv, str1[3]);599#endif600 601  rv = strncasecmp(str1, str2, 3);602  assert(rv == 0);603  ASSERT_ZERO_LABEL(rv);604 605  char s1[] = "AbZ";606  char s2[] = "aBy";607  dfsan_set_label(i_label, &s1[2], 1);608  dfsan_set_label(j_label, &s2[2], 1);609 610  rv = strncasecmp(s1, s2, 0);611  assert(rv == 0); // Compare zero chars.612  ASSERT_ZERO_LABEL(rv);613 614  rv = strncasecmp(s1, s2, 1);615  assert(rv == 0); // 'A' == 'a'616  ASSERT_ZERO_LABEL(rv);617 618  rv = strncasecmp(s1, s2, 2);619  assert(rv == 0); // 'b' == 'B'620  ASSERT_ZERO_LABEL(rv);621 622  rv = strncasecmp(s1, s2, 3);623  assert(rv > 0); // 'Z' > 'y'624#ifdef STRICT_DATA_DEPENDENCIES625  ASSERT_ZERO_LABEL(rv);626#else627  ASSERT_LABEL(rv, dfsan_union(i_label, j_label));628  ASSERT_EQ_ORIGIN(rv, s1[2]);629#endif630}631 632void test_strchr() {633  char str1[] = "str1";634  dfsan_set_label(i_label, &str1[3], 1);635 636  char *p1 = str1;637  char c = 'r';638  dfsan_set_label(k_label, &c, sizeof(c));639 640  char *crv = strchr(p1, c);641  assert(crv == &str1[2]);642#ifdef STRICT_DATA_DEPENDENCIES643  ASSERT_ZERO_LABEL(crv);644#else645  ASSERT_LABEL(crv, k_label);646  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&crv, c);647#endif648 649  dfsan_set_label(j_label, &p1, sizeof(p1));650  crv = strchr(p1, 'r');651  assert(crv == &str1[2]);652  ASSERT_LABEL(crv, j_label);653  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&crv, p1);654 655  crv = strchr(p1, '1');656  assert(crv == &str1[3]);657#ifdef STRICT_DATA_DEPENDENCIES658  ASSERT_LABEL(crv, j_label);659  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&crv, p1);660#else661  ASSERT_LABEL(crv, i_j_label);662  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&crv, str1[3]);663#endif664 665  crv = strchr(p1, 'x');666  assert(!crv);667#ifdef STRICT_DATA_DEPENDENCIES668  ASSERT_LABEL(crv, j_label);669  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&crv, p1);670#else671  ASSERT_LABEL(crv, i_j_label);672  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&crv, str1[3]);673#endif674 675  // `man strchr` says:676  // The terminating null byte is considered part of the string, so that if c677  // is specified as '\0', these functions return a pointer to the terminator.678  crv = strchr(p1, '\0');679  assert(crv == &str1[4]);680#ifdef STRICT_DATA_DEPENDENCIES681  ASSERT_LABEL(crv, j_label);682  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&crv, p1);683#else684  ASSERT_LABEL(crv, i_j_label);685  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&crv, str1[3]);686#endif687}688 689void test_recvmmsg() {690  int sockfds[2];691  int ret = socketpair(AF_UNIX, SOCK_DGRAM, 0, sockfds);692  assert(ret != -1);693 694  // Setup messages to send.695  struct mmsghdr smmsg[2] = {};696  char sbuf0[] = "abcdefghijkl";697  struct iovec siov0[2] = {{&sbuf0[0], 4}, {&sbuf0[4], 4}};698  smmsg[0].msg_hdr.msg_iov = siov0;699  smmsg[0].msg_hdr.msg_iovlen = 2;700  char sbuf1[] = "1234567890";701  struct iovec siov1[1] = {{&sbuf1[0], 7}};702  smmsg[1].msg_hdr.msg_iov = siov1;703  smmsg[1].msg_hdr.msg_iovlen = 1;704 705  // Send messages.706  int sent_msgs = sendmmsg(sockfds[0], smmsg, 2, 0);707  assert(sent_msgs == 2);708 709  // Setup receive buffers.710  struct mmsghdr rmmsg[2] = {};711  char rbuf0[128];712  struct iovec riov0[2] = {{&rbuf0[0], 4}, {&rbuf0[4], 4}};713  rmmsg[0].msg_hdr.msg_iov = riov0;714  rmmsg[0].msg_hdr.msg_iovlen = 2;715  char rbuf1[128];716  struct iovec riov1[1] = {{&rbuf1[0], 16}};717  rmmsg[1].msg_hdr.msg_iov = riov1;718  rmmsg[1].msg_hdr.msg_iovlen = 1;719  struct timespec timeout = {1, 1};720  dfsan_set_label(i_label, rbuf0, sizeof(rbuf0));721  dfsan_set_label(i_label, rbuf1, sizeof(rbuf1));722  dfsan_set_label(i_label, &rmmsg[0].msg_len, sizeof(rmmsg[0].msg_len));723  dfsan_set_label(i_label, &rmmsg[1].msg_len, sizeof(rmmsg[1].msg_len));724  dfsan_set_label(i_label, &timeout, sizeof(timeout));725 726  dfsan_origin msg_len0_o = dfsan_get_origin((long)(rmmsg[0].msg_len));727  dfsan_origin msg_len1_o = dfsan_get_origin((long)(rmmsg[1].msg_len));728#ifndef ORIGIN_TRACKING729  (void)msg_len0_o;730  (void)msg_len1_o;731#endif732 733  // Receive messages and check labels.734  int received_msgs = recvmmsg(sockfds[1], rmmsg, 2, 0, &timeout);735  assert(received_msgs == sent_msgs);736  assert(rmmsg[0].msg_len == smmsg[0].msg_len);737  assert(rmmsg[1].msg_len == smmsg[1].msg_len);738  assert(memcmp(sbuf0, rbuf0, 8) == 0);739  assert(memcmp(sbuf1, rbuf1, 7) == 0);740  ASSERT_ZERO_LABEL(received_msgs);741  ASSERT_ZERO_LABEL(rmmsg[0].msg_len);742  ASSERT_ZERO_LABEL(rmmsg[1].msg_len);743  ASSERT_READ_ZERO_LABEL(&rbuf0[0], 8);744  ASSERT_READ_LABEL(&rbuf0[8], 1, i_label);745  ASSERT_READ_ZERO_LABEL(&rbuf1[0], 7);746  ASSERT_READ_LABEL(&rbuf1[7], 1, i_label);747  ASSERT_LABEL(timeout.tv_sec, i_label);748  ASSERT_LABEL(timeout.tv_nsec, i_label);749 750  ASSERT_ORIGIN((long)(rmmsg[0].msg_len), msg_len0_o);751  ASSERT_ORIGIN((long)(rmmsg[1].msg_len), msg_len1_o);752 753  close(sockfds[0]);754  close(sockfds[1]);755}756 757void test_recvmsg() {758  int sockfds[2];759  int ret = socketpair(AF_UNIX, SOCK_DGRAM, 0, sockfds);760  assert(ret != -1);761 762  char sbuf[] = "abcdefghijkl";763  struct iovec siovs[2] = {{&sbuf[0], 4}, {&sbuf[4], 4}};764  struct msghdr smsg = {};765  smsg.msg_iov = siovs;766  smsg.msg_iovlen = 2;767 768  ssize_t sent = sendmsg(sockfds[0], &smsg, 0);769  assert(sent > 0);770 771  {772    char rpbuf[2];773    struct iovec peek_iov;774    peek_iov.iov_base = rpbuf;775    peek_iov.iov_len = 2;776 777    struct msghdr peek_header = {};778    peek_header.msg_iov = &peek_iov;779    peek_header.msg_iovlen = 1;780 781    dfsan_set_label(i_label, rpbuf, sizeof(rpbuf));782    dfsan_set_label(i_label, &peek_header, sizeof(peek_header));783 784    DEFINE_AND_SAVE_ORIGINS(peek_header)785 786    ssize_t received = recvmsg(sockfds[1], &peek_header, MSG_PEEK | MSG_TRUNC);787    assert(received == sent);788    assert(memcmp(sbuf, rpbuf, 2) == 0);789    ASSERT_ZERO_LABEL(received);790    ASSERT_READ_ZERO_LABEL(&peek_header, sizeof(peek_header));791    ASSERT_READ_ZERO_LABEL(&rpbuf[0], 0);792 793    ASSERT_SAVED_ORIGINS(peek_header)794  }795 796  {797    char rbuf[128];798    struct iovec riovs[2] = {{&rbuf[0], 4}, {&rbuf[4], 4}};799    struct msghdr rmsg = {};800    rmsg.msg_iov = riovs;801    rmsg.msg_iovlen = 2;802 803    dfsan_set_label(i_label, rbuf, sizeof(rbuf));804    dfsan_set_label(i_label, &rmsg, sizeof(rmsg));805 806    DEFINE_AND_SAVE_ORIGINS(rmsg)807 808    ssize_t received = recvmsg(sockfds[1], &rmsg, 0);809    assert(received == sent);810    assert(memcmp(sbuf, rbuf, 8) == 0);811    ASSERT_ZERO_LABEL(received);812    ASSERT_READ_ZERO_LABEL(&rmsg, sizeof(rmsg));813    ASSERT_READ_ZERO_LABEL(&rbuf[0], 8);814    ASSERT_READ_LABEL(&rbuf[8], 1, i_label);815 816    ASSERT_SAVED_ORIGINS(rmsg)817  }818 819  close(sockfds[0]);820  close(sockfds[1]);821}822 823void test_read() {824  char buf[16];825  dfsan_set_label(i_label, buf, 1);826  dfsan_set_label(j_label, buf + 15, 1);827 828  DEFINE_AND_SAVE_ORIGINS(buf)829  ASSERT_LABEL(buf[0], i_label);830  ASSERT_LABEL(buf[15], j_label);831 832  int fd = open("/dev/zero", O_RDONLY);833  int rv = read(fd, buf, sizeof(buf));834  assert(rv == sizeof(buf));835  ASSERT_ZERO_LABEL(rv);836  ASSERT_ZERO_LABEL(buf[0]);837  ASSERT_ZERO_LABEL(buf[15]);838  ASSERT_SAVED_ORIGINS(buf)839  close(fd);840}841 842void test_pread() {843  char buf[16];844  dfsan_set_label(i_label, buf, 1);845  dfsan_set_label(j_label, buf + 15, 1);846 847  DEFINE_AND_SAVE_ORIGINS(buf)848  ASSERT_LABEL(buf[0], i_label);849  ASSERT_LABEL(buf[15], j_label);850 851  int fd = open("/bin/sh", O_RDONLY);852  int rv = pread(fd, buf, sizeof(buf), 0);853  assert(rv == sizeof(buf));854  ASSERT_ZERO_LABEL(rv);855  ASSERT_ZERO_LABEL(buf[0]);856  ASSERT_ZERO_LABEL(buf[15]);857  ASSERT_SAVED_ORIGINS(buf)858  close(fd);859}860 861void test_dlopen() {862  void *map = dlopen(NULL, RTLD_NOW);863  assert(map);864  ASSERT_ZERO_LABEL(map);865  dlclose(map);866  map = dlopen("/nonexistent", RTLD_NOW);867  assert(!map);868  ASSERT_ZERO_LABEL(map);869}870 871void test_clock_gettime() {872  struct timespec tp;873  dfsan_set_label(j_label, ((char *)&tp) + 3, 1);874  dfsan_origin origin = dfsan_get_origin((long)(((char *)&tp)[3]));875#ifndef ORIGIN_TRACKING876  (void)origin;877#endif878  int t = clock_gettime(CLOCK_REALTIME, &tp);879  assert(t == 0);880  ASSERT_ZERO_LABEL(t);881  ASSERT_ZERO_LABEL(((char *)&tp)[3]);882  ASSERT_ORIGIN(((char *)&tp)[3], origin);883}884 885void test_ctime_r() {886  char *buf = (char*) malloc(64);887  time_t t = 0;888 889  DEFINE_AND_SAVE_ORIGINS(buf)890  dfsan_origin t_o = dfsan_get_origin((long)t);891 892  char *ret = ctime_r(&t, buf);893  ASSERT_ZERO_LABEL(ret);894  assert(buf == ret);895  ASSERT_READ_ZERO_LABEL(buf, strlen(buf) + 1);896  ASSERT_SAVED_ORIGINS(buf)897 898  dfsan_set_label(i_label, &t, sizeof(t));899  t_o = dfsan_get_origin((long)t);900  ret = ctime_r(&t, buf);901  ASSERT_ZERO_LABEL(ret);902  ASSERT_READ_LABEL(buf, strlen(buf) + 1, i_label);903  for (int i = 0; i < strlen(buf) + 1; ++i)904    ASSERT_ORIGIN(buf[i], t_o);905 906  t = 0;907  dfsan_set_label(j_label, &buf, sizeof(&buf));908  dfsan_origin buf_ptr_o = dfsan_get_origin((long)buf);909#ifndef ORIGIN_TRACKING910  (void)buf_ptr_o;911#endif912  ret = ctime_r(&t, buf);913  ASSERT_LABEL(ret, j_label);914  ASSERT_ORIGIN(ret, buf_ptr_o);915  ASSERT_READ_ZERO_LABEL(buf, strlen(buf) + 1);916  for (int i = 0; i < strlen(buf) + 1; ++i)917    ASSERT_ORIGIN(buf[i], t_o);918}919 920static int write_callback_count = 0;921static int last_fd;922static const unsigned char *last_buf;923static size_t last_count;924 925void write_callback(int fd, const void *buf, size_t count) {926  write_callback_count++;927 928  last_fd = fd;929  last_buf = (const unsigned char*) buf;930  last_count = count;931}932 933void test_dfsan_set_write_callback() {934  char a_buf[] = "Sample chars";935  int a_buf_len = strlen(a_buf);936 937  int fd = open("/dev/null", O_WRONLY);938 939  dfsan_set_write_callback(write_callback);940 941  write_callback_count = 0;942 943  DEFINE_AND_SAVE_ORIGINS(a_buf)944 945  // Callback should be invoked on every call to write().946  int res = write(fd, a_buf, a_buf_len);947  assert(write_callback_count == 1);948  ASSERT_READ_ZERO_LABEL(&res, sizeof(res));949  ASSERT_READ_ZERO_LABEL(&last_fd, sizeof(last_fd));950  ASSERT_READ_ZERO_LABEL(last_buf, sizeof(last_buf));951 952  for (int i = 0; i < a_buf_len; ++i)953    ASSERT_ORIGIN(last_buf[i], a_buf_o[i]);954 955  ASSERT_ZERO_ORIGINS(&last_count, sizeof(last_count));956  last_fd = 0;957  last_buf = 0;958  last_count = 0;959 960  char b_buf[] = "Other chars";961  int b_buf_len = strlen(b_buf);962  // Create a separate variable so we can taint the pointer.963  // We would always get a shadow of 0 for b_buf because it is a constant.964  const unsigned char *buf = (const unsigned char *)b_buf;965 966  // Add a label to write() arguments.  Check that the labels are readable from967  // the values passed to the callback.968  dfsan_set_label(i_label, &fd, sizeof(fd));969  dfsan_set_label(j_label, &buf, sizeof(buf)); // ptr970  dfsan_set_label(k_label, &(b_buf[3]), 1);    // content971  dfsan_set_label(m_label, &b_buf_len, sizeof(b_buf_len));972 973  dfsan_origin fd_o = dfsan_get_origin((long)fd);974  dfsan_origin b_buf3_o = dfsan_get_origin((long)(b_buf[3]));975  dfsan_origin b_buf_len_o = dfsan_get_origin((long)b_buf_len);976#ifndef ORIGIN_TRACKING977  (void)fd_o;978  (void)b_buf3_o;979  (void)b_buf_len_o;980#endif981  DEFINE_AND_SAVE_ORIGINS(b_buf)982 983  res = write(fd, buf, b_buf_len);984  assert(write_callback_count == 2);985  assert(last_fd == fd);986  assert(last_buf == (const unsigned char *)b_buf);987  assert(last_count == b_buf_len);988 989  ASSERT_READ_ZERO_LABEL(&res, sizeof(res));990  ASSERT_READ_LABEL(&last_fd, sizeof(last_fd), i_label);991  ASSERT_READ_LABEL(&last_buf, sizeof(&last_buf), j_label);      // ptr992  ASSERT_READ_LABEL(last_buf, last_count, k_label);              // content993  ASSERT_READ_LABEL(&last_buf[3], sizeof(last_buf[3]), k_label); // content994  ASSERT_READ_LABEL(&last_count, sizeof(last_count), m_label);995  ASSERT_ZERO_ORIGINS(&res, sizeof(res));996  ASSERT_INIT_ORIGINS(&last_fd, sizeof(last_fd), fd_o);997  ASSERT_INIT_ORIGINS(&last_buf[3], sizeof(last_buf[3]), b_buf3_o);998 999  // Origins are assigned for every 4 contiguous 4-aligned bytes. After1000  // appending src to dst, origins of src can overwrite origins of dst if their1001  // application adddresses are within an aligned range. Other origins are not1002  // changed.1003  for (int i = 0; i < b_buf_len; ++i) {1004    size_t i_addr = size_t(&last_buf[i]);1005    if (((size_t(&last_buf[3]) & ~3UL) > i_addr) ||1006        (((size_t(&last_buf[3]) + 4) & ~3UL) <= i_addr))1007      ASSERT_ORIGIN(last_buf[i], b_buf_o[i]);1008  }1009 1010  ASSERT_INIT_ORIGINS(&last_count, sizeof(last_count), b_buf_len_o);1011 1012  dfsan_set_write_callback(NULL);1013}1014 1015void test_fgets() {1016  char *buf = (char*) malloc(128);1017  FILE *f = fopen("/etc/passwd", "r");1018  dfsan_set_label(j_label, buf, 1);1019  DEFINE_AND_SAVE_N_ORIGINS(buf, 128)1020 1021  char *ret = fgets(buf, sizeof(buf), f);1022  assert(ret == buf);1023  ASSERT_ZERO_LABEL(ret);1024  ASSERT_EQ_ORIGIN(ret, buf);1025  ASSERT_READ_ZERO_LABEL(buf, 128);1026  ASSERT_SAVED_N_ORIGINS(buf, 128)1027 1028  dfsan_set_label(j_label, &buf, sizeof(&buf));1029  ret = fgets(buf, sizeof(buf), f);1030  ASSERT_LABEL(ret, j_label);1031  ASSERT_EQ_ORIGIN(ret, buf);1032  ASSERT_SAVED_N_ORIGINS(buf, 128)1033 1034  fclose(f);1035  free(buf);1036}1037 1038void test_getcwd() {1039  char buf[1024];1040  char *ptr = buf;1041  dfsan_set_label(i_label, buf + 2, 2);1042  DEFINE_AND_SAVE_ORIGINS(buf)1043 1044  char* ret = getcwd(buf, sizeof(buf));1045  assert(ret == buf);1046  assert(ret[0] == '/');1047  ASSERT_ZERO_LABEL(ret);1048  ASSERT_EQ_ORIGIN(ret, buf);1049  ASSERT_READ_ZERO_LABEL(buf + 2, 2);1050  ASSERT_SAVED_ORIGINS(buf)1051 1052  dfsan_set_label(i_label, &ptr, sizeof(ptr));1053  ret = getcwd(ptr, sizeof(buf));1054  ASSERT_LABEL(ret, i_label);1055  ASSERT_EQ_ORIGIN(ret, ptr);1056  ASSERT_SAVED_ORIGINS(buf)1057}1058 1059void test_get_current_dir_name() {1060  char* ret = get_current_dir_name();1061  assert(ret);1062  assert(ret[0] == '/');1063  ASSERT_READ_ZERO_LABEL(ret, strlen(ret) + 1);1064  ASSERT_ZERO_LABEL(ret);1065}1066 1067void test_getentropy() {1068  char buf[64];1069  dfsan_set_label(i_label, buf + 2, 2);1070  DEFINE_AND_SAVE_ORIGINS(buf)1071#if __GLIBC_PREREQ(2, 25)1072  // glibc >= 2.25 has getentropy()1073  int ret = getentropy(buf, sizeof(buf));1074  ASSERT_ZERO_LABEL(ret);1075  if (ret == 0) {1076    ASSERT_READ_ZERO_LABEL(buf + 2, 2);1077    ASSERT_SAVED_ORIGINS(buf)1078  }1079#endif1080}1081 1082void test_gethostname() {1083  char buf[1024];1084  dfsan_set_label(i_label, buf + 2, 2);1085  DEFINE_AND_SAVE_ORIGINS(buf)1086  int ret = gethostname(buf, sizeof(buf));1087  assert(ret == 0);1088  ASSERT_ZERO_LABEL(ret);1089  ASSERT_READ_ZERO_LABEL(buf + 2, 2);1090  ASSERT_SAVED_ORIGINS(buf)1091}1092 1093void test_getrlimit() {1094  struct rlimit rlim;1095  dfsan_set_label(i_label, &rlim, sizeof(rlim));1096  DEFINE_AND_SAVE_ORIGINS(rlim);1097  int ret = getrlimit(RLIMIT_CPU, &rlim);1098  assert(ret == 0);1099  ASSERT_ZERO_LABEL(ret);1100  ASSERT_READ_ZERO_LABEL(&rlim, sizeof(rlim));1101  ASSERT_SAVED_ORIGINS(rlim)1102}1103 1104void test_getrusage() {1105  struct rusage usage;1106  dfsan_set_label(i_label, &usage, sizeof(usage));1107  DEFINE_AND_SAVE_ORIGINS(usage);1108  int ret = getrusage(RUSAGE_SELF, &usage);1109  assert(ret == 0);1110  ASSERT_ZERO_LABEL(ret);1111  ASSERT_READ_ZERO_LABEL(&usage, sizeof(usage));1112  ASSERT_SAVED_ORIGINS(usage)1113}1114 1115void test_strcpy() {1116  char src[] = "hello world";1117  char dst[sizeof(src) + 2];1118  char *p_dst = dst;1119  dfsan_set_label(0, src, sizeof(src));1120  dfsan_set_label(0, dst, sizeof(dst));1121  dfsan_set_label(k_label, &p_dst, sizeof(p_dst));1122  dfsan_set_label(i_label, src + 2, 1);1123  dfsan_set_label(j_label, src + 3, 1);1124  dfsan_set_label(j_label, dst + 4, 1);1125  dfsan_set_label(i_label, dst + 12, 1);1126  char *ret = strcpy(p_dst, src);1127  assert(ret == dst);1128  assert(strcmp(src, dst) == 0);1129  ASSERT_LABEL(ret, k_label);1130  ASSERT_EQ_ORIGIN(ret, p_dst);1131  for (int i = 0; i < strlen(src) + 1; ++i) {1132    assert(dfsan_get_label(dst[i]) == dfsan_get_label(src[i]));1133    if (dfsan_get_label(dst[i]))1134      assert(dfsan_get_init_origin(&dst[i]) == dfsan_get_origin(src[i]));1135  }1136  // Note: if strlen(src) + 1 were used instead to compute the first untouched1137  // byte of dest, the label would be I|J. This is because strlen() might1138  // return a non-zero label, and because by default pointer labels are not1139  // ignored on loads.1140  ASSERT_LABEL(dst[12], i_label);1141}1142 1143void test_strtol() {1144  char non_number_buf[] = "ab ";1145  char *endptr = NULL;1146  long int ret = strtol(non_number_buf, &endptr, 10);1147  assert(ret == 0);1148  assert(endptr == non_number_buf);1149  ASSERT_ZERO_LABEL(ret);1150 1151  char buf[] = "1234578910";1152  int base = 10;1153  dfsan_set_label(k_label, &base, sizeof(base));1154  ret = strtol(buf, &endptr, base);1155  assert(ret == 1234578910);1156  assert(endptr == buf + 10);1157  ASSERT_LABEL(ret, k_label);1158  ASSERT_EQ_ORIGIN(ret, base);1159 1160  dfsan_set_label(i_label, buf + 1, 1);1161  dfsan_set_label(j_label, buf + 10, 1);1162  ret = strtol(buf, &endptr, 10);1163  assert(ret == 1234578910);1164  assert(endptr == buf + 10);1165  ASSERT_LABEL(ret, i_j_label);1166  ASSERT_EQ_ORIGIN(ret, buf[1]);1167}1168 1169void test_strtoll() {1170  char non_number_buf[] = "ab ";1171  char *endptr = NULL;1172  long long int ret = strtoll(non_number_buf, &endptr, 10);1173  assert(ret == 0);1174  assert(endptr == non_number_buf);1175  ASSERT_ZERO_LABEL(ret);1176 1177  char buf[] = "1234578910 ";1178  int base = 10;1179  dfsan_set_label(k_label, &base, sizeof(base));1180  ret = strtoll(buf, &endptr, base);1181  assert(ret == 1234578910);1182  assert(endptr == buf + 10);1183  ASSERT_LABEL(ret, k_label);1184  ASSERT_EQ_ORIGIN(ret, base);1185 1186  dfsan_set_label(i_label, buf + 1, 1);1187  dfsan_set_label(j_label, buf + 2, 1);1188  ret = strtoll(buf, &endptr, 10);1189  assert(ret == 1234578910);1190  assert(endptr == buf + 10);1191  ASSERT_LABEL(ret, i_j_label);1192  ASSERT_EQ_ORIGIN(ret, buf[1]);1193}1194 1195void test_strtoul() {1196  char non_number_buf[] = "xy ";1197  char *endptr = NULL;1198  long unsigned int ret = strtoul(non_number_buf, &endptr, 16);1199  assert(ret == 0);1200  assert(endptr == non_number_buf);1201  ASSERT_ZERO_LABEL(ret);1202 1203  char buf[] = "ffffffffffffaa";1204  int base = 16;1205  dfsan_set_label(k_label, &base, sizeof(base));1206  ret = strtoul(buf, &endptr, base);1207  assert(ret == 72057594037927850);1208  assert(endptr == buf + 14);1209  ASSERT_LABEL(ret, k_label);1210  ASSERT_EQ_ORIGIN(ret, base);1211 1212  dfsan_set_label(i_label, buf + 1, 1);1213  dfsan_set_label(j_label, buf + 2, 1);1214  ret = strtoul(buf, &endptr, 16);1215  assert(ret == 72057594037927850);1216  assert(endptr == buf + 14);1217  ASSERT_LABEL(ret, i_j_label);1218  ASSERT_EQ_ORIGIN(ret, buf[1]);1219}1220 1221void test_strtoull() {1222  char non_number_buf[] = "xy ";1223  char *endptr = NULL;1224  long long unsigned int ret = strtoull(non_number_buf, &endptr, 16);1225  assert(ret == 0);1226  assert(endptr == non_number_buf);1227  ASSERT_ZERO_LABEL(ret);1228 1229  char buf[] = "ffffffffffffffaa";1230  int base = 16;1231  dfsan_set_label(k_label, &base, sizeof(base));1232  ret = strtoull(buf, &endptr, base);1233  assert(ret == 0xffffffffffffffaa);1234  assert(endptr == buf + 16);1235  ASSERT_LABEL(ret, k_label);1236  ASSERT_EQ_ORIGIN(ret, base);1237 1238  dfsan_set_label(i_label, buf + 1, 1);1239  dfsan_set_label(j_label, buf + 2, 1);1240  ret = strtoull(buf, &endptr, 16);1241  assert(ret == 0xffffffffffffffaa);1242  assert(endptr == buf + 16);1243  ASSERT_LABEL(ret, i_j_label);1244  ASSERT_EQ_ORIGIN(ret, buf[1]);1245}1246 1247void test_strtod() {1248  char non_number_buf[] = "ab ";1249  char *endptr = NULL;1250  double ret = strtod(non_number_buf, &endptr);1251  assert(ret == 0);1252  assert(endptr == non_number_buf);1253  ASSERT_ZERO_LABEL(ret);1254 1255  char buf[] = "12345.76 foo";1256  dfsan_set_label(i_label, buf + 1, 1);1257  dfsan_set_label(j_label, buf + 6, 1);1258  ret = strtod(buf, &endptr);1259  assert(ret == 12345.76);1260  assert(endptr == buf + 8);1261  ASSERT_LABEL(ret, i_j_label);1262  ASSERT_EQ_ORIGIN(ret, buf[1]);1263}1264 1265void test_time() {1266  time_t t = 0;1267  dfsan_set_label(i_label, &t, 1);1268  DEFINE_AND_SAVE_ORIGINS(t)1269  time_t ret = time(&t);1270  assert(ret == t);1271  assert(ret > 0);1272  ASSERT_ZERO_LABEL(ret);1273  ASSERT_ZERO_LABEL(t);1274  ASSERT_SAVED_ORIGINS(t)1275}1276 1277void test_inet_pton() {1278  char addr4[] = "127.0.0.1";1279  dfsan_set_label(i_label, addr4 + 3, 1);1280  struct in_addr in4;1281  int ret4 = inet_pton(AF_INET, addr4, &in4);1282  assert(ret4 == 1);1283  ASSERT_ZERO_LABEL(ret4);1284  ASSERT_READ_LABEL(&in4, sizeof(in4), i_label);1285  ASSERT_ORIGINS(&in4, sizeof(in4), dfsan_get_origin((long)(addr4[3])))1286  assert(in4.s_addr == htonl(0x7f000001));1287 1288  char addr6[] = "::1";1289  dfsan_set_label(j_label, addr6 + 3, 1);1290  struct in6_addr in6;1291  int ret6 = inet_pton(AF_INET6, addr6, &in6);1292  assert(ret6 == 1);1293  ASSERT_ZERO_LABEL(ret6);1294  ASSERT_READ_LABEL(((char *) &in6) + sizeof(in6) - 1, 1, j_label);1295  ASSERT_ORIGINS(&in6, sizeof(in6), dfsan_get_origin((long)(addr6[3])))1296}1297 1298void test_localtime_r() {1299  time_t t0 = 1384800998;1300  struct tm t1;1301  dfsan_set_label(i_label, &t0, sizeof(t0));1302  dfsan_origin t0_o = dfsan_get_origin((long)t0);1303  struct tm *pt1 = &t1;1304  dfsan_set_label(j_label, &pt1, sizeof(pt1));1305  dfsan_origin pt1_o = dfsan_get_origin((long)pt1);1306 1307#ifndef ORIGIN_TRACKING1308  (void)t0_o;1309  (void)pt1_o;1310#endif1311 1312  struct tm *ret = localtime_r(&t0, pt1);1313  assert(ret == &t1);1314  assert(t1.tm_min == 56);1315  ASSERT_LABEL(ret, j_label);1316  ASSERT_INIT_ORIGIN(&ret, pt1_o);1317  ASSERT_READ_LABEL(&ret, sizeof(ret), j_label);1318  ASSERT_LABEL(t1.tm_mon, i_label);1319  ASSERT_ORIGIN(t1.tm_mon, t0_o);1320}1321 1322void test_getpwuid_r() {1323  struct passwd pwd;1324  char buf[1024];1325  struct passwd *result;1326 1327  dfsan_set_label(i_label, &pwd, 4);1328  DEFINE_AND_SAVE_ORIGINS(pwd)1329  DEFINE_AND_SAVE_ORIGINS(buf)1330  int ret = getpwuid_r(0, &pwd, buf, sizeof(buf), &result);1331  assert(ret == 0);1332  assert(strcmp(pwd.pw_name, "root") == 0);1333  assert(result == &pwd);1334  ASSERT_ZERO_LABEL(ret);1335  ASSERT_READ_ZERO_LABEL(&pwd, 4);1336  ASSERT_SAVED_ORIGINS(pwd)1337  ASSERT_SAVED_ORIGINS(buf)1338}1339 1340void test_epoll_wait() {1341  // Set up a pipe to monitor with epoll.1342  int pipe_fds[2];1343  int ret = pipe(pipe_fds);1344  assert(ret != -1);1345 1346  // Configure epoll to monitor the pipe.1347  int epfd = epoll_create1(0);1348  assert(epfd != -1);1349  struct epoll_event event;1350  event.events = EPOLLIN;1351  event.data.fd = pipe_fds[0];1352  ret = epoll_ctl(epfd, EPOLL_CTL_ADD, pipe_fds[0], &event);1353  assert(ret != -1);1354 1355  // Test epoll_wait when no events have occurred.1356  event = {};1357  dfsan_set_label(i_label, &event, sizeof(event));1358  DEFINE_AND_SAVE_ORIGINS(event)1359  ret = epoll_wait(epfd, &event, /*maxevents=*/1, /*timeout=*/0);1360  assert(ret == 0);1361  assert(event.events == 0);1362  assert(event.data.fd == 0);1363  ASSERT_ZERO_LABEL(ret);1364  ASSERT_READ_LABEL(&event, sizeof(event), i_label);1365  ASSERT_SAVED_ORIGINS(event)1366 1367  // Test epoll_wait when an event occurs.1368  write(pipe_fds[1], "x", 1);1369  ret = epoll_wait(epfd, &event, /*maxevents=*/1, /*timeout=*/0);1370  assert(ret == 1);1371  assert(event.events == EPOLLIN);1372  assert(event.data.fd == pipe_fds[0]);1373  ASSERT_ZERO_LABEL(ret);1374  ASSERT_READ_ZERO_LABEL(&event, sizeof(event));1375  ASSERT_SAVED_ORIGINS(event)1376 1377  // Clean up.1378  close(epfd);1379  close(pipe_fds[0]);1380  close(pipe_fds[1]);1381}1382 1383void test_poll() {1384  struct pollfd fd;1385  fd.fd = 0;1386  fd.events = POLLIN;1387  dfsan_set_label(i_label, &fd.revents, sizeof(fd.revents));1388  DEFINE_AND_SAVE_ORIGINS(fd)1389  int ret = poll(&fd, 1, 1);1390  ASSERT_ZERO_LABEL(ret);1391  ASSERT_ZERO_LABEL(fd.revents);1392  ASSERT_SAVED_ORIGINS(fd)1393  assert(ret >= 0);1394}1395 1396void test_select() {1397  struct timeval t;1398  fd_set fds;1399  t.tv_sec = 2;1400  FD_SET(0, &fds);1401  dfsan_set_label(i_label, &fds, sizeof(fds));1402  dfsan_set_label(j_label, &t, sizeof(t));1403  DEFINE_AND_SAVE_ORIGINS(fds)1404  DEFINE_AND_SAVE_ORIGINS(t)1405  int ret = select(1, &fds, NULL, NULL, &t);1406  assert(ret >= 0);1407  ASSERT_ZERO_LABEL(ret);1408  ASSERT_ZERO_LABEL(t.tv_sec);1409  ASSERT_READ_ZERO_LABEL(&fds, sizeof(fds));1410  ASSERT_SAVED_ORIGINS(fds)1411  ASSERT_SAVED_ORIGINS(t)1412}1413 1414void test_sched_getaffinity() {1415  cpu_set_t mask;1416  dfsan_set_label(j_label, &mask, 1);1417  DEFINE_AND_SAVE_ORIGINS(mask)1418  int ret = sched_getaffinity(0, sizeof(mask), &mask);1419  assert(ret == 0);1420  ASSERT_ZERO_LABEL(ret);1421  ASSERT_READ_ZERO_LABEL(&mask, sizeof(mask));1422  ASSERT_SAVED_ORIGINS(mask)1423}1424 1425void test_sigemptyset() {1426  sigset_t set;1427  dfsan_set_label(j_label, &set, 1);1428  DEFINE_AND_SAVE_ORIGINS(set)1429  int ret = sigemptyset(&set);1430  assert(ret == 0);1431  ASSERT_ZERO_LABEL(ret);1432  ASSERT_READ_ZERO_LABEL(&set, sizeof(set));1433  ASSERT_SAVED_ORIGINS(set)1434}1435 1436static void SignalHandler(int signo) {}1437 1438static void SignalAction(int signo, siginfo_t *si, void *uc) {}1439 1440void test_sigaction() {1441  struct sigaction newact_with_sigaction = {};1442  newact_with_sigaction.sa_flags = SA_SIGINFO;1443  newact_with_sigaction.sa_sigaction = SignalAction;1444 1445  // Set sigaction to be SignalAction, save the last one into origin_act1446  struct sigaction origin_act;1447  dfsan_set_label(j_label, &origin_act, 1);1448  DEFINE_AND_SAVE_ORIGINS(origin_act)1449  int ret = sigaction(SIGUSR1, &newact_with_sigaction, &origin_act);1450  assert(ret == 0);1451  ASSERT_ZERO_LABEL(ret);1452  ASSERT_READ_ZERO_LABEL(&origin_act, sizeof(origin_act));1453  ASSERT_SAVED_ORIGINS(origin_act)1454 1455  struct sigaction newact_with_sighandler = {};1456  newact_with_sighandler.sa_handler = SignalHandler;1457 1458  // Set sigaction to be SignalHandler, check the last one is SignalAction1459  struct sigaction oldact;1460  assert(0 == sigaction(SIGUSR1, &newact_with_sighandler, &oldact));1461  assert(oldact.sa_sigaction == SignalAction);1462  assert(oldact.sa_flags & SA_SIGINFO);1463 1464  // Set SIG_IGN or SIG_DFL, and check the previous one is expected.1465  newact_with_sighandler.sa_handler = SIG_IGN;1466  assert(0 == sigaction(SIGUSR1, &newact_with_sighandler, &oldact));1467  assert(oldact.sa_handler == SignalHandler);1468  assert((oldact.sa_flags & SA_SIGINFO) == 0);1469 1470  newact_with_sighandler.sa_handler = SIG_DFL;1471  assert(0 == sigaction(SIGUSR1, &newact_with_sighandler, &oldact));1472  assert(oldact.sa_handler == SIG_IGN);1473  assert((oldact.sa_flags & SA_SIGINFO) == 0);1474 1475  // Restore sigaction to the orginal setting, check the last one is SignalHandler1476  assert(0 == sigaction(SIGUSR1, &origin_act, &oldact));1477  assert(oldact.sa_handler == SIG_DFL);1478  assert((oldact.sa_flags & SA_SIGINFO) == 0);1479}1480 1481void test_signal() {1482  // Set signal to be SignalHandler, save the previous one into1483  // old_signal_handler.1484  sighandler_t old_signal_handler = signal(SIGHUP, SignalHandler);1485  ASSERT_ZERO_LABEL(old_signal_handler);1486 1487  // Set SIG_IGN or SIG_DFL, and check the previous one is expected.1488  assert(SignalHandler == signal(SIGHUP, SIG_DFL));1489  assert(SIG_DFL == signal(SIGHUP, SIG_IGN));1490 1491  // Restore signal to old_signal_handler.1492  assert(SIG_IGN == signal(SIGHUP, old_signal_handler));1493}1494 1495void test_sigaltstack() {1496  stack_t old_altstack = {};1497  dfsan_set_label(j_label, &old_altstack, sizeof(old_altstack));1498  DEFINE_AND_SAVE_ORIGINS(old_altstack)1499  int ret = sigaltstack(NULL, &old_altstack);1500  assert(ret == 0);1501  ASSERT_ZERO_LABEL(ret);1502  ASSERT_READ_ZERO_LABEL(&old_altstack, sizeof(old_altstack));1503  ASSERT_SAVED_ORIGINS(old_altstack)1504}1505 1506void test_gettimeofday() {1507  struct timeval tv;1508  struct timezone tz;1509  dfsan_set_label(i_label, &tv, sizeof(tv));1510  dfsan_set_label(j_label, &tz, sizeof(tz));1511  DEFINE_AND_SAVE_ORIGINS(tv)1512  DEFINE_AND_SAVE_ORIGINS(tz)1513  int ret = gettimeofday(&tv, &tz);1514  assert(ret == 0);1515  ASSERT_READ_ZERO_LABEL(&tv, sizeof(tv));1516  ASSERT_READ_ZERO_LABEL(&tz, sizeof(tz));1517  ASSERT_SAVED_ORIGINS(tv)1518  ASSERT_SAVED_ORIGINS(tz)1519}1520 1521void *pthread_create_test_cb(void *p) {1522  assert(p == (void *)1);1523  ASSERT_ZERO_LABEL(p);1524  return (void *)2;1525}1526 1527void test_pthread_create() {1528  pthread_t pt;1529  int create_ret = pthread_create(&pt, 0, pthread_create_test_cb, (void *)1);1530  assert(create_ret == 0);1531  ASSERT_ZERO_LABEL(create_ret);1532  void *cbrv;1533  dfsan_set_label(i_label, &cbrv, sizeof(cbrv));1534  DEFINE_AND_SAVE_ORIGINS(cbrv)1535  int joint_ret = pthread_join(pt, &cbrv);1536  assert(joint_ret == 0);1537  assert(cbrv == (void *)2);1538  ASSERT_ZERO_LABEL(joint_ret);1539  ASSERT_ZERO_LABEL(cbrv);1540  ASSERT_SAVED_ORIGINS(cbrv);1541}1542 1543// Tested by test_pthread_create().  This empty function is here to appease the1544// check-wrappers script.1545void test_pthread_join() {}1546 1547int dl_iterate_phdr_test_cb(struct dl_phdr_info *info, size_t size,1548                            void *data) {1549  assert(data == (void *)3);1550  ASSERT_ZERO_LABEL(info);1551  ASSERT_ZERO_LABEL(size);1552  ASSERT_ZERO_LABEL(data);1553  return 0;1554}1555 1556void test_dl_iterate_phdr() {1557  dl_iterate_phdr(dl_iterate_phdr_test_cb, (void *)3);1558}1559 1560// On glibc < 2.27, this symbol is not available.  Mark it weak so we can skip1561// testing in this case.1562__attribute__((weak)) extern "C" void _dl_get_tls_static_info(size_t *sizep,1563                                                              size_t *alignp);1564 1565void test__dl_get_tls_static_info() {1566  if (!_dl_get_tls_static_info)1567    return;1568  size_t sizep = 0, alignp = 0;1569  dfsan_set_label(i_label, &sizep, sizeof(sizep));1570  dfsan_set_label(i_label, &alignp, sizeof(alignp));1571  dfsan_origin sizep_o = dfsan_get_origin(sizep);1572  dfsan_origin alignp_o = dfsan_get_origin(alignp);1573#ifndef ORIGIN_TRACKING1574  (void)sizep_o;1575  (void)alignp_o;1576#endif1577  _dl_get_tls_static_info(&sizep, &alignp);1578  ASSERT_ZERO_LABEL(sizep);1579  ASSERT_ZERO_LABEL(alignp);1580  ASSERT_ORIGIN(sizep, sizep_o);1581  ASSERT_ORIGIN(alignp, alignp_o);1582}1583 1584void test_strrchr() {1585  char str1[] = "str1str1";1586 1587  char *p = str1;1588  dfsan_set_label(j_label, &p, sizeof(p));1589 1590  char *rv = strrchr(p, 'r');1591  assert(rv == &str1[6]);1592  ASSERT_LABEL(rv, j_label);1593  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, p);1594 1595  char c = 'r';1596  dfsan_set_label(k_label, &c, sizeof(c));1597  rv = strrchr(str1, c);1598  assert(rv == &str1[6]);1599#ifdef STRICT_DATA_DEPENDENCIES1600  ASSERT_ZERO_LABEL(rv);1601#else1602  ASSERT_LABEL(rv, k_label);1603  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, c);1604#endif1605 1606  dfsan_set_label(i_label, &str1[7], 1);1607 1608  rv = strrchr(str1, 'r');1609  assert(rv == &str1[6]);1610#ifdef STRICT_DATA_DEPENDENCIES1611  ASSERT_ZERO_LABEL(rv);1612#else1613  ASSERT_LABEL(rv, i_label);1614  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, str1[7]);1615#endif1616}1617 1618void test_strstr() {1619  char str1[] = "str1str1";1620 1621  char *p1 = str1;1622  dfsan_set_label(k_label, &p1, sizeof(p1));1623  char *rv = strstr(p1, "1s");1624  assert(rv == &str1[3]);1625  ASSERT_LABEL(rv, k_label);1626  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, p1);1627 1628  char str2[] = "1s";1629  char *p2 = str2;1630  dfsan_set_label(m_label, &p2, sizeof(p2));1631  rv = strstr(str1, p2);1632  assert(rv == &str1[3]);1633#ifdef STRICT_DATA_DEPENDENCIES1634  ASSERT_ZERO_LABEL(rv);1635#else1636  ASSERT_LABEL(rv, m_label);1637  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, p2);1638#endif1639 1640  dfsan_set_label(n_label, &str2[0], 1);1641  rv = strstr(str1, str2);1642  assert(rv == &str1[3]);1643#ifdef STRICT_DATA_DEPENDENCIES1644  ASSERT_ZERO_LABEL(rv);1645#else1646  ASSERT_LABEL(rv, n_label);1647  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, str2[0]);1648#endif1649 1650  dfsan_set_label(i_label, &str1[3], 1);1651  dfsan_set_label(j_label, &str1[5], 1);1652 1653  rv = strstr(str1, "1s");1654  assert(rv == &str1[3]);1655#ifdef STRICT_DATA_DEPENDENCIES1656  ASSERT_ZERO_LABEL(rv);1657#else1658  ASSERT_LABEL(rv, i_label);1659  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, str1[3]);1660#endif1661 1662  rv = strstr(str1, "2s");1663  assert(rv == NULL);1664#ifdef STRICT_DATA_DEPENDENCIES1665  ASSERT_ZERO_LABEL(rv);1666#else1667  ASSERT_LABEL(rv, i_j_label);1668  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, str1[3]);1669#endif1670}1671 1672void test_strpbrk() {1673  char s[] = "abcdefg";1674  char accept[] = "123fd";1675 1676  char *p_s = s;1677  char *p_accept = accept;1678 1679  dfsan_set_label(n_label, &p_accept, sizeof(p_accept));1680 1681  char *rv = strpbrk(p_s, p_accept);1682  assert(rv == &s[3]);1683#ifdef STRICT_DATA_DEPENDENCIES1684  ASSERT_ZERO_LABEL(rv);1685#else1686  ASSERT_LABEL(rv, n_label);1687  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, p_accept);1688#endif1689 1690  dfsan_set_label(m_label, &p_s, sizeof(p_s));1691 1692  rv = strpbrk(p_s, p_accept);1693  assert(rv == &s[3]);1694#ifdef STRICT_DATA_DEPENDENCIES1695  ASSERT_LABEL(rv, m_label);1696  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, p_s);1697#else1698  ASSERT_LABEL(rv, dfsan_union(m_label, n_label));1699  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, p_s);1700#endif1701 1702  dfsan_set_label(i_label, &s[5], 1);1703  dfsan_set_label(j_label, &accept[1], 1);1704 1705  rv = strpbrk(s, accept);1706  assert(rv == &s[3]);1707#ifdef STRICT_DATA_DEPENDENCIES1708  ASSERT_ZERO_LABEL(rv);1709#else1710  ASSERT_LABEL(rv, j_label);1711  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, accept[1]);1712#endif1713 1714  char *ps = s;1715  dfsan_set_label(j_label, &ps, sizeof(ps));1716 1717  rv = strpbrk(ps, "123gf");1718  assert(rv == &s[5]);1719#ifdef STRICT_DATA_DEPENDENCIES1720  ASSERT_LABEL(rv, j_label);1721#else1722  ASSERT_LABEL(rv, i_j_label);1723  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, s[5]);1724#endif1725 1726  rv = strpbrk(ps, "123");1727  assert(rv == NULL);1728#ifdef STRICT_DATA_DEPENDENCIES1729  ASSERT_ZERO_LABEL(rv);1730#else1731  ASSERT_LABEL(rv, i_j_label);1732  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, s[5]);1733#endif1734}1735 1736void test_strsep() {1737  char *s = strdup("Hello world/");1738  char *delim = strdup(" /");1739 1740  char *p_s = s;1741  char *base = s;1742  char *p_delim = delim;1743 1744  // taint delim bytes1745  dfsan_set_label(i_label, p_delim, strlen(p_delim));1746  // taint delim pointer1747  dfsan_set_label(j_label, &p_delim, sizeof(p_delim));1748  // taint the string data bytes1749  dfsan_set_label(k_label, s, 5);1750  // taint the string pointer1751  dfsan_set_label(m_label, &p_s, sizeof(p_s));1752 1753  char *rv = strsep(&p_s, p_delim);1754  assert(rv == &base[0]);1755#ifdef STRICT_DATA_DEPENDENCIES1756  ASSERT_LABEL(rv, m_label);1757  ASSERT_READ_LABEL(rv, strlen(rv), k_label);1758#else1759  ASSERT_LABEL(rv, dfsan_union(dfsan_union(i_label, j_label),1760                               dfsan_union(k_label, m_label)));1761  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, p_s);1762#endif1763 1764  // taint the remaining string's pointer1765  char **pp_s = &p_s;1766  char **pp_s_base = pp_s;1767  dfsan_set_label(n_label, pp_s, sizeof(pp_s));1768 1769  rv = strsep(pp_s, p_delim);1770 1771  assert(rv == &base[6]);1772#ifdef STRICT_DATA_DEPENDENCIES1773  ASSERT_LABEL(rv, n_label);1774  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, *pp_s);1775#else1776  ASSERT_LABEL(rv, dfsan_union(dfsan_union(i_label, j_label), n_label));1777  ASSERT_INIT_ORIGIN_EQ_ORIGIN(&rv, *pp_s);1778#endif1779}1780 1781void test_memchr() {1782  char str1[] = "str1";1783  dfsan_set_label(i_label, &str1[3], 1);1784  dfsan_set_label(j_label, &str1[4], 1);1785 1786  char *crv = (char *) memchr(str1, 'r', sizeof(str1));1787  assert(crv == &str1[2]);1788  ASSERT_ZERO_LABEL(crv);1789 1790  char c = 'r';1791  dfsan_set_label(k_label, &c, sizeof(c));1792  crv = (char *)memchr(str1, c, sizeof(str1));1793  assert(crv == &str1[2]);1794#ifdef STRICT_DATA_DEPENDENCIES1795  ASSERT_ZERO_LABEL(crv);1796#else1797  ASSERT_LABEL(crv, k_label);1798  ASSERT_EQ_ORIGIN(crv, c);1799#endif1800 1801  char *ptr = str1;1802  dfsan_set_label(k_label, &ptr, sizeof(ptr));1803  crv = (char *)memchr(ptr, 'r', sizeof(str1));1804  assert(crv == &str1[2]);1805  ASSERT_LABEL(crv, k_label);1806  ASSERT_EQ_ORIGIN(crv, ptr);1807 1808  crv = (char *) memchr(str1, '1', sizeof(str1));1809  assert(crv == &str1[3]);1810#ifdef STRICT_DATA_DEPENDENCIES1811  ASSERT_ZERO_LABEL(crv);1812#else1813  ASSERT_LABEL(crv, i_label);1814  ASSERT_EQ_ORIGIN(crv, str1[3]);1815#endif1816 1817  crv = (char *) memchr(str1, 'x', sizeof(str1));1818  assert(!crv);1819#ifdef STRICT_DATA_DEPENDENCIES1820  ASSERT_ZERO_LABEL(crv);1821#else1822  ASSERT_LABEL(crv, i_j_label);1823  ASSERT_EQ_ORIGIN(crv, str1[3]);1824#endif1825}1826 1827void alarm_handler(int unused) {1828  ;1829}1830 1831void test_nanosleep() {1832  struct timespec req, rem;1833  req.tv_sec = 1;1834  req.tv_nsec = 0;1835  dfsan_set_label(i_label, &rem, sizeof(rem));1836  DEFINE_AND_SAVE_ORIGINS(rem)1837 1838  // non interrupted1839  int rv = nanosleep(&req, &rem);1840  assert(rv == 0);1841  ASSERT_ZERO_LABEL(rv);1842  ASSERT_READ_LABEL(&rem, 1, i_label);1843  ASSERT_SAVED_ORIGINS(rem)1844 1845  // interrupted by an alarm1846  signal(SIGALRM, alarm_handler);1847  req.tv_sec = 3;1848  alarm(1);1849  rv = nanosleep(&req, &rem);1850  assert(rv == -1);1851  ASSERT_ZERO_LABEL(rv);1852  ASSERT_READ_ZERO_LABEL(&rem, sizeof(rem));1853  ASSERT_SAVED_ORIGINS(rem)1854}1855 1856void test_socketpair() {1857  int fd[2];1858  dfsan_origin fd_o[2];1859 1860  dfsan_set_label(i_label, fd, sizeof(fd));1861  fd_o[0] = dfsan_get_origin((long)(fd[0]));1862  fd_o[1] = dfsan_get_origin((long)(fd[1]));1863  int rv = socketpair(PF_LOCAL, SOCK_STREAM, 0, fd);1864  assert(rv == 0);1865  ASSERT_ZERO_LABEL(rv);1866  ASSERT_READ_ZERO_LABEL(fd, sizeof(fd));1867  ASSERT_ORIGIN(fd[0], fd_o[0]);1868  ASSERT_ORIGIN(fd[1], fd_o[1]);1869}1870 1871void test_getpeername() {1872  int sockfds[2];1873  int ret = socketpair(AF_UNIX, SOCK_DGRAM, 0, sockfds);1874  assert(ret != -1);1875 1876  struct sockaddr addr = {};1877  socklen_t addrlen = sizeof(addr);1878  dfsan_set_label(i_label, &addr, addrlen);1879  dfsan_set_label(i_label, &addrlen, sizeof(addrlen));1880  DEFINE_AND_SAVE_ORIGINS(addr)1881  DEFINE_AND_SAVE_ORIGINS(addrlen)1882 1883  ret = getpeername(sockfds[0], &addr, &addrlen);1884  assert(ret != -1);1885  ASSERT_ZERO_LABEL(ret);1886  ASSERT_ZERO_LABEL(addrlen);1887  assert(addrlen < sizeof(addr));1888  ASSERT_READ_ZERO_LABEL(&addr, addrlen);1889  ASSERT_READ_LABEL(((char *)&addr) + addrlen, 1, i_label);1890  ASSERT_SAVED_ORIGINS(addr)1891  ASSERT_SAVED_ORIGINS(addrlen)1892 1893  close(sockfds[0]);1894  close(sockfds[1]);1895}1896 1897void test_getsockname() {1898  int sockfd = socket(AF_UNIX, SOCK_DGRAM, 0);1899  assert(sockfd != -1);1900 1901  struct sockaddr addr = {};1902  socklen_t addrlen = sizeof(addr);1903  dfsan_set_label(i_label, &addr, addrlen);1904  dfsan_set_label(i_label, &addrlen, sizeof(addrlen));1905  DEFINE_AND_SAVE_ORIGINS(addr)1906  DEFINE_AND_SAVE_ORIGINS(addrlen)1907  int ret = getsockname(sockfd, &addr, &addrlen);1908  assert(ret != -1);1909  ASSERT_ZERO_LABEL(ret);1910  ASSERT_ZERO_LABEL(addrlen);1911  assert(addrlen < sizeof(addr));1912  ASSERT_READ_ZERO_LABEL(&addr, addrlen);1913  ASSERT_READ_LABEL(((char *)&addr) + addrlen, 1, i_label);1914  ASSERT_SAVED_ORIGINS(addr)1915  ASSERT_SAVED_ORIGINS(addrlen)1916 1917  close(sockfd);1918}1919 1920void test_getsockopt() {1921  int sockfd = socket(AF_UNIX, SOCK_DGRAM, 0);1922  assert(sockfd != -1);1923 1924  int optval[2] = {-1, -1};1925  socklen_t optlen = sizeof(optval);1926  dfsan_set_label(i_label, &optval, sizeof(optval));1927  dfsan_set_label(i_label, &optlen, sizeof(optlen));1928  DEFINE_AND_SAVE_ORIGINS(optval)1929  DEFINE_AND_SAVE_ORIGINS(optlen)1930  int ret = getsockopt(sockfd, SOL_SOCKET, SO_KEEPALIVE, &optval, &optlen);1931  assert(ret != -1);1932  assert(optlen == sizeof(int));1933  assert(optval[0] == 0);1934  assert(optval[1] == -1);1935  ASSERT_ZERO_LABEL(ret);1936  ASSERT_ZERO_LABEL(optlen);1937  ASSERT_ZERO_LABEL(optval[0]);1938  ASSERT_LABEL(optval[1], i_label);1939  ASSERT_SAVED_ORIGINS(optval)1940  ASSERT_SAVED_ORIGINS(optlen)1941 1942  close(sockfd);1943}1944 1945void test_write() {1946  int fd = open("/dev/null", O_WRONLY);1947 1948  char buf[] = "a string";1949  int len = strlen(buf);1950 1951  // The result of a write always unlabeled.1952  int res = write(fd, buf, len);1953  assert(res > 0);1954  ASSERT_ZERO_LABEL(res);1955 1956  // Label all arguments to write().1957  dfsan_set_label(i_label, &(buf[3]), 1);1958  dfsan_set_label(j_label, &fd, sizeof(fd));1959  dfsan_set_label(k_label, &len, sizeof(len));1960 1961  // The value returned by write() should have no label.1962  res = write(fd, buf, len);1963  ASSERT_ZERO_LABEL(res);1964 1965  close(fd);1966}1967 1968template <class T>1969void test_sprintf_chunk(const char* expected, const char* format, T arg) {1970  char buf[512];1971  memset(buf, 'a', sizeof(buf));1972 1973  char padded_expected[512];1974  strcpy(padded_expected, "foo ");1975  strcat(padded_expected, expected);1976  strcat(padded_expected, " bar");1977 1978  char padded_format[512];1979  strcpy(padded_format, "foo ");1980  strcat(padded_format, format);1981  strcat(padded_format, " bar");1982 1983  // Non labelled arg.1984  assert(sprintf(buf, padded_format,  arg) == strlen(padded_expected));1985  assert(strcmp(buf, padded_expected) == 0);1986  ASSERT_READ_LABEL(buf, strlen(padded_expected), 0);1987  memset(buf, 'a', sizeof(buf));1988 1989  // Labelled arg.1990  dfsan_set_label(i_label, &arg, sizeof(arg));1991  dfsan_origin a_o = dfsan_get_origin((long)(arg));1992#ifndef ORIGIN_TRACKING1993  (void)a_o;1994#endif1995  assert(sprintf(buf, padded_format,  arg) == strlen(padded_expected));1996  assert(strcmp(buf, padded_expected) == 0);1997  ASSERT_READ_LABEL(buf, 4, 0);1998  ASSERT_READ_LABEL(buf + 4, strlen(padded_expected) - 8, i_label);1999  ASSERT_INIT_ORIGINS(buf + 4, strlen(padded_expected) - 8, a_o);2000  ASSERT_READ_LABEL(buf + (strlen(padded_expected) - 4), 4, 0);2001}2002 2003void test_sprintf() {2004  char buf[2048];2005  memset(buf, 'a', sizeof(buf));2006 2007  // Test formatting (no conversion specifier).2008  assert(sprintf(buf, "Hello world!") == 12);2009  assert(strcmp(buf, "Hello world!") == 0);2010  ASSERT_READ_LABEL(buf, sizeof(buf), 0);2011 2012  // Test for extra arguments.2013  assert(sprintf(buf, "Hello world!", 42, "hello") == 12);2014  assert(strcmp(buf, "Hello world!") == 0);2015  ASSERT_READ_LABEL(buf, sizeof(buf), 0);2016 2017  // Test formatting & label propagation (multiple conversion specifiers): %s,2018  // %d, %n, %f, and %%.2019  const char* s = "world";2020  int m = 8;2021  int d = 27;2022  dfsan_set_label(k_label, (void *) (s + 1), 2);2023  dfsan_origin s_o = dfsan_get_origin((long)(s[1]));2024  dfsan_set_label(i_label, &m, sizeof(m));2025  dfsan_origin m_o = dfsan_get_origin((long)m);2026  dfsan_set_label(j_label, &d, sizeof(d));2027  dfsan_origin d_o = dfsan_get_origin((long)d);2028#ifndef ORIGIN_TRACKING2029  (void)s_o;2030  (void)m_o;2031  (void)d_o;2032#endif2033  int n;2034  int r = sprintf(buf, "hello %s, %-d/%d/%d %f %% %n%d", s, 2014, m, d,2035                  12345.6781234, &n, 1000);2036  assert(r == 42);2037  assert(strcmp(buf, "hello world, 2014/8/27 12345.678123 % 1000") == 0);2038  ASSERT_READ_LABEL(buf, 7, 0);2039  ASSERT_READ_LABEL(buf + 7, 2, k_label);2040  ASSERT_INIT_ORIGINS(buf + 7, 2, s_o);2041  ASSERT_READ_LABEL(buf + 9, 9, 0);2042  ASSERT_READ_LABEL(buf + 18, 1, i_label);2043  ASSERT_INIT_ORIGINS(buf + 18, 1, m_o);2044  ASSERT_READ_LABEL(buf + 19, 1, 0);2045  ASSERT_READ_LABEL(buf + 20, 2, j_label);2046  ASSERT_INIT_ORIGINS(buf + 20, 2, d_o);2047  ASSERT_READ_LABEL(buf + 22, 15, 0);2048  ASSERT_LABEL(r, 0);2049  assert(n == 38);2050 2051  // Test formatting & label propagation (single conversion specifier, with2052  // additional length and precision modifiers).2053  test_sprintf_chunk("-559038737", "%d", 0xdeadbeef);2054  test_sprintf_chunk("3735928559", "%u", 0xdeadbeef);2055  test_sprintf_chunk("12345", "%i", 12345);2056  test_sprintf_chunk("751", "%o", 0751);2057  test_sprintf_chunk("babe", "%x", 0xbabe);2058  test_sprintf_chunk("0000BABE", "%.8X", 0xbabe);2059  test_sprintf_chunk("-17", "%hhd", 0xdeadbeef);2060  test_sprintf_chunk("-16657", "%hd", 0xdeadbeef);2061  test_sprintf_chunk("deadbeefdeadbeef", "%lx", 0xdeadbeefdeadbeef);2062  test_sprintf_chunk("0xdeadbeefdeadbeef", "%p",2063                 (void *)  0xdeadbeefdeadbeef);2064  test_sprintf_chunk("18446744073709551615", "%ju", (intmax_t) -1);2065  test_sprintf_chunk("18446744073709551615", "%zu", (size_t) -1);2066  test_sprintf_chunk("18446744073709551615", "%tu", (size_t) -1);2067 2068  test_sprintf_chunk("0x1.f9acffa7eb6bfp-4", "%a", 0.123456);2069  test_sprintf_chunk("0X1.F9ACFFA7EB6BFP-4", "%A", 0.123456);2070  test_sprintf_chunk("0.12346", "%.5f", 0.123456);2071  test_sprintf_chunk("0.123456", "%g", 0.123456);2072  test_sprintf_chunk("1.234560e-01", "%e", 0.123456);2073  test_sprintf_chunk("1.234560E-01", "%E", 0.123456);2074  test_sprintf_chunk("0.1234567891234560", "%.16Lf",2075                     (long double) 0.123456789123456);2076 2077  test_sprintf_chunk("z", "%c", 'z');2078 2079  // %n, %s, %d, %f, and %% already tested2080 2081  // Test formatting with width passed as an argument.2082  r = sprintf(buf, "hi %*d my %*s friend %.*f", 3, 1, 6, "dear", 4, 3.14159265359);2083  assert(r == 30);2084  assert(strcmp(buf, "hi   1 my   dear friend 3.1416") == 0);2085}2086 2087void test_snprintf() {2088  char buf[2048];2089  memset(buf, 'a', sizeof(buf));2090  dfsan_set_label(0, buf, sizeof(buf));2091  const char* s = "world";2092  int y = 2014;2093  int m = 8;2094  int d = 27;2095  dfsan_set_label(k_label, (void *) (s + 1), 2);2096  dfsan_origin s_o = dfsan_get_origin((long)(s[1]));2097  dfsan_set_label(i_label, &y, sizeof(y));2098  dfsan_origin y_o = dfsan_get_origin((long)y);2099  dfsan_set_label(j_label, &m, sizeof(m));2100  dfsan_origin m_o = dfsan_get_origin((long)m);2101#ifndef ORIGIN_TRACKING2102  (void)s_o;2103  (void)y_o;2104  (void)m_o;2105#endif2106  int r = snprintf(buf, 19, "hello %s, %-d/   %d/%d %f", s, y, m, d,2107                   12345.6781234);2108  // The return value is the number of bytes that would have been written to2109  // the final string if enough space had been available.2110  assert(r == 38);2111  assert(memcmp(buf, "hello world, 2014/", 19) == 0);2112  ASSERT_READ_LABEL(buf, 7, 0);2113  ASSERT_READ_LABEL(buf + 7, 2, k_label);2114  ASSERT_INIT_ORIGINS(buf + 7, 2, s_o);2115  ASSERT_READ_LABEL(buf + 9, 4, 0);2116  ASSERT_READ_LABEL(buf + 13, 4, i_label);2117  ASSERT_INIT_ORIGINS(buf + 13, 4, y_o);2118  ASSERT_READ_LABEL(buf + 17, 2, 0);2119  ASSERT_LABEL(r, 0);2120}2121 2122template <class T>2123void test_sscanf_chunk(T expected, const char *format, char *input,2124                       int items_num) {2125  char padded_input[512];2126  strcpy(padded_input, "foo ");2127  strcat(padded_input, input);2128  strcpy(padded_input, "@");2129  strcat(padded_input, input);2130  strcat(padded_input, " bar");2131 2132  char padded_format[512];2133  strcpy(padded_format, "foo ");2134  // Swap the first '%' for '%*' so this input is skipped.2135  strcpy(padded_format, "%*");2136  strcat(padded_format, format + 1);2137  strcpy(padded_format, "@");2138  strcat(padded_format, format);2139  strcat(padded_format, " bar");2140 2141  char *s = padded_input + 4;2142  T arg;2143  memset(&arg, 0, sizeof(arg));2144  dfsan_set_label(i_label, (void *)(padded_input), strlen(padded_input));2145  dfsan_set_label(j_label, (void *)(padded_format), strlen(padded_format));2146  dfsan_origin a_o = dfsan_get_origin((long)(*s));2147#ifndef ORIGIN_TRACKING2148  (void)a_o;2149#else2150  assert(a_o != 0);2151#endif2152  int rv = sscanf(padded_input, padded_format, &arg);2153  assert(rv == items_num);2154  assert(arg == expected);2155  ASSERT_READ_LABEL(&arg, sizeof(arg), i_label);2156  ASSERT_INIT_ORIGINS(&arg, 1, a_o);2157}2158 2159void test_sscanf() {2160  char buf[2048];2161  char buf_out[2048];2162  memset(buf, 'a', sizeof(buf));2163  memset(buf_out, 'a', sizeof(buf_out));2164 2165  // Test formatting2166  strcpy(buf, "Hello world!");2167  assert(sscanf(buf, "%s", buf_out) == 1);2168  assert(strcmp(buf, "Hello world!") == 0);2169  assert(strcmp(buf_out, "Hello") == 0);2170  ASSERT_READ_LABEL(buf, sizeof(buf), 0);2171  ASSERT_READ_LABEL(buf_out, sizeof(buf_out), 0);2172 2173  // Test for extra arguments.2174  assert(sscanf(buf, "%s", buf_out, 42, "hello") == 1);2175  assert(strcmp(buf, "Hello world!") == 0);2176  assert(strcmp(buf_out, "Hello") == 0);2177  ASSERT_READ_LABEL(buf, sizeof(buf), 0);2178  ASSERT_READ_LABEL(buf_out, sizeof(buf_out), 0);2179 2180  // Test formatting & label propagation (multiple conversion specifiers): %s,2181  // %d, %n, %f, and %%.2182  int n;2183  strcpy(buf, "hello world, 42 2014/8/31 12345.678123 % 1000");2184  char *s = buf + 6; //starts with world2185  int y = 0;2186  int m = 0;2187  int d = 0;2188  float fval;2189  int val = 0;2190  dfsan_set_label(k_label, (void *)(s + 1), 2); // buf[7]-b[9]2191  dfsan_origin s_o = dfsan_get_origin((long)(s[1]));2192  assert(s[10] == '2');2193  dfsan_set_label(i_label, (void *)(s + 10), 4);    // 20142194  dfsan_origin y_o = dfsan_get_origin((long)s[10]); // buf[16]2195  assert(s[17] == '3');2196  dfsan_set_label(j_label, (void *)(s + 17), 2);    // 312197  dfsan_origin d_o = dfsan_get_origin((long)s[17]); // buf[23]2198  assert(s[20] == '1');2199  dfsan_set_label(m_label, (void *)(s + 20), 5);    // 123452200  dfsan_origin f_o = dfsan_get_origin((long)s[20]); //buf[26]2201 2202#ifndef ORIGIN_TRACKING2203  (void)s_o;2204  (void)y_o;2205  (void)d_o;2206  (void)f_o;2207#else2208  assert(s_o != 0);2209  assert(y_o != 0);2210  assert(d_o != 0);2211  assert(f_o != 0);2212#endif2213  int r = sscanf(buf, "hello %s %*d %d/%d/%d %f %% %n%d", buf_out, &y, &m, &d,2214                 &fval, &n, &val);2215  assert(r == 6);2216  assert(strcmp(buf_out, "world,") == 0);2217  assert(y == 2014);2218  assert(m == 8);2219  assert(d == 31);2220  assert(fval > 12300.0f);2221  assert(fval < 12400.0f);2222  ASSERT_READ_LABEL(buf_out, 1, 0);2223  ASSERT_READ_LABEL(buf_out + 1, 2, k_label);2224  ASSERT_INIT_ORIGINS(buf_out + 1, 2, s_o);2225  ASSERT_READ_LABEL(&y, sizeof(y), i_label);2226  ASSERT_INIT_ORIGINS(&y, sizeof(y), y_o);2227  ASSERT_READ_LABEL(&d, sizeof(d), j_label);2228  ASSERT_INIT_ORIGINS(&d, sizeof(d), d_o);2229  ASSERT_READ_LABEL(&fval, sizeof(fval), m_label);2230  ASSERT_INIT_ORIGINS(&fval, sizeof(fval), f_o);2231  ASSERT_READ_LABEL(&val, 4, 0);2232  ASSERT_LABEL(r, 0);2233  assert(n == 41);2234  assert(val == 1000);2235 2236  // Test formatting & label propagation (single conversion specifier, with2237  // additional length and precision modifiers).2238  char input_buf[512];2239  char *input_ptr = input_buf;2240  strcpy(input_buf, "-559038737");2241  test_sscanf_chunk(-559038737, "%d", input_ptr, 1);2242  strcpy(input_buf, "3735928559");2243  test_sscanf_chunk(3735928559, "%u", input_ptr, 1);2244  strcpy(input_buf, "12345");2245  test_sscanf_chunk(12345, "%i", input_ptr, 1);2246  strcpy(input_buf, "0751");2247  test_sscanf_chunk(489, "%o", input_ptr, 1);2248  strcpy(input_buf, "0xbabe");2249  test_sscanf_chunk(47806, "%x", input_ptr, 1);2250  strcpy(input_buf, "0x0000BABE");2251  test_sscanf_chunk(47806, "%10X", input_ptr, 1);2252  strcpy(input_buf, "3735928559");2253  test_sscanf_chunk((char)-17, "%hhd", input_ptr, 1);2254  strcpy(input_buf, "3735928559");2255  test_sscanf_chunk((short)-16657, "%hd", input_ptr, 1);2256  strcpy(input_buf, "0xdeadbeefdeadbeef");2257  test_sscanf_chunk(0xdeadbeefdeadbeefL, "%lx", input_buf, 1);2258  test_sscanf_chunk((void *)0xdeadbeefdeadbeefL, "%p", input_buf, 1);2259 2260  intmax_t _x = (intmax_t)-1;2261  char _buf[256];2262  memset(_buf, 0, sizeof(_buf));2263  sprintf(_buf, "%ju", _x);2264  test_sscanf_chunk((intmax_t)18446744073709551615, "%ju", _buf, 1);2265  memset(_buf, 0, sizeof(_buf));2266  size_t _y = (size_t)-1;2267  sprintf(_buf, "%zu", _y);2268  test_sscanf_chunk((size_t)18446744073709551615, "%zu", _buf, 1);2269  memset(_buf, 0, sizeof(_buf));2270  ptrdiff_t _z = (size_t)-1;2271  sprintf(_buf, "%tu", _z);2272  test_sscanf_chunk((ptrdiff_t)18446744073709551615, "%tu", _buf, 1);2273 2274  strcpy(input_buf, "0.123456");2275  test_sscanf_chunk((float)0.123456, "%8f", input_ptr, 1);2276  test_sscanf_chunk((float)0.123456, "%g", input_ptr, 1);2277  test_sscanf_chunk((float)1.234560e-01, "%e", input_ptr, 1);2278  test_sscanf_chunk((char)'z', "%c", "z", 1);2279 2280  // %n, %s, %d, %f, and %% already tested2281}2282 2283// Tested by a separate source file.  This empty function is here to appease the2284// check-wrappers script.2285void test_fork() {}2286 2287int main(void) {2288  i_label = 1;2289  j_label = 2;2290  k_label = 4;2291  m_label = 8;2292  n_label = 16;2293  i_j_label = dfsan_union(i_label, j_label);2294  assert(i_j_label != i_label);2295  assert(i_j_label != j_label);2296  assert(i_j_label != k_label);2297 2298  test__dl_get_tls_static_info();2299  test_bcmp();2300  test_clock_gettime();2301  test_ctime_r();2302  test_dfsan_set_write_callback();2303  test_dl_iterate_phdr();2304  test_dlopen();2305  test_epoll_wait();2306  test_fgets();2307  test_fork();2308  test_fstat();2309  test_get_current_dir_name();2310  test_getcwd();2311  test_getentropy();2312  test_gethostname();2313  test_getpeername();2314  test_getpwuid_r();2315  test_getrlimit();2316  test_getrusage();2317  test_getsockname();2318  test_getsockopt();2319  test_gettimeofday();2320  test_inet_pton();2321  test_localtime_r();2322  test_memchr();2323  test_memcmp();2324  test_memcpy();2325  test_memmove();2326  test_memset();2327  test_nanosleep();2328  test_poll();2329  test_pread();2330  test_pthread_create();2331  test_pthread_join();2332  test_read();2333  test_recvmmsg();2334  test_recvmsg();2335  test_sched_getaffinity();2336  test_select();2337  test_sigaction();2338  test_signal();2339  test_sigaltstack();2340  test_sigemptyset();2341  test_snprintf();2342  test_sscanf();2343  test_socketpair();2344  test_sprintf();2345  test_stat();2346  test_strcasecmp();2347  test_strchr();2348  test_strcmp();2349  test_strcat();2350  test_strncat(5);2351  test_strncat(2);2352  test_strcpy();2353  test_strdup();2354  test_strlen();2355  test_strnlen();2356  test_strncasecmp();2357  test_strncmp();2358  test_strncpy();2359  test_strpbrk();2360  test_strsep();2361  test_strrchr();2362  test_strstr();2363  test_strtod();2364  test_strtol();2365  test_strtoll();2366  test_strtoul();2367  test_strtoull();2368  test_time();2369  test_write();2370}2371