Home | History | Annotate | Download | only in unit_tests
      1 //===-- tsan_printf_test.cc -----------------------------------------------===//
      2 //
      3 //                     The LLVM Compiler Infrastructure
      4 //
      5 // This file is distributed under the University of Illinois Open Source
      6 // License. See LICENSE.TXT for details.
      7 //
      8 //===----------------------------------------------------------------------===//
      9 //
     10 // This file is a part of ThreadSanitizer (TSan), a race detector.
     11 //
     12 //===----------------------------------------------------------------------===//
     13 #include "tsan_rtl.h"
     14 #include "gtest/gtest.h"
     15 
     16 #include <string.h>
     17 #include <limits.h>
     18 
     19 namespace __tsan {
     20 
     21 TEST(Printf, Basic) {
     22   char buf[1024];
     23   uptr len = internal_snprintf(buf, sizeof(buf),
     24       "a%db%zdc%ue%zuf%xh%zxq%pe%sr",
     25       (int)-1, (long)-2, // NOLINT
     26       (unsigned)-4, (unsigned long)5, // NOLINT
     27       (unsigned)10, (unsigned long)11, // NOLINT
     28       (void*)0x123, "_string_");
     29   EXPECT_EQ(len, strlen(buf));
     30   EXPECT_EQ(0, strcmp(buf, "a-1b-2c4294967292e5fahbq"
     31                            "0x000000000123e_string_r"));
     32 }
     33 
     34 TEST(Printf, OverflowStr) {
     35   char buf[] = "123456789";
     36   uptr len = internal_snprintf(buf, 4, "%s", "abcdef");  // NOLINT
     37   EXPECT_EQ(len, (uptr)6);
     38   EXPECT_EQ(0, strcmp(buf, "abc"));
     39   EXPECT_EQ(buf[3], 0);
     40   EXPECT_EQ(buf[4], '5');
     41   EXPECT_EQ(buf[5], '6');
     42   EXPECT_EQ(buf[6], '7');
     43   EXPECT_EQ(buf[7], '8');
     44   EXPECT_EQ(buf[8], '9');
     45   EXPECT_EQ(buf[9], 0);
     46 }
     47 
     48 TEST(Printf, OverflowInt) {
     49   char buf[] = "123456789";
     50   internal_snprintf(buf, 4, "%d", -123456789);  // NOLINT
     51   EXPECT_EQ(0, strcmp(buf, "-12"));
     52   EXPECT_EQ(buf[3], 0);
     53   EXPECT_EQ(buf[4], '5');
     54   EXPECT_EQ(buf[5], '6');
     55   EXPECT_EQ(buf[6], '7');
     56   EXPECT_EQ(buf[7], '8');
     57   EXPECT_EQ(buf[8], '9');
     58   EXPECT_EQ(buf[9], 0);
     59 }
     60 
     61 TEST(Printf, OverflowUint) {
     62   char buf[] = "123456789";
     63   internal_snprintf(buf, 4, "a%zx", (unsigned long)0x123456789);  // NOLINT
     64   EXPECT_EQ(0, strcmp(buf, "a12"));
     65   EXPECT_EQ(buf[3], 0);
     66   EXPECT_EQ(buf[4], '5');
     67   EXPECT_EQ(buf[5], '6');
     68   EXPECT_EQ(buf[6], '7');
     69   EXPECT_EQ(buf[7], '8');
     70   EXPECT_EQ(buf[8], '9');
     71   EXPECT_EQ(buf[9], 0);
     72 }
     73 
     74 TEST(Printf, OverflowPtr) {
     75   char buf[] = "123456789";
     76   internal_snprintf(buf, 4, "%p", (void*)0x123456789);  // NOLINT
     77   EXPECT_EQ(0, strcmp(buf, "0x0"));
     78   EXPECT_EQ(buf[3], 0);
     79   EXPECT_EQ(buf[4], '5');
     80   EXPECT_EQ(buf[5], '6');
     81   EXPECT_EQ(buf[6], '7');
     82   EXPECT_EQ(buf[7], '8');
     83   EXPECT_EQ(buf[8], '9');
     84   EXPECT_EQ(buf[9], 0);
     85 }
     86 
     87 template<typename T>
     88 static void TestMinMax(const char *fmt, T min, T max) {
     89   char buf[1024];
     90   uptr len = internal_snprintf(buf, sizeof(buf), fmt, min, max);
     91   char buf2[1024];
     92   snprintf(buf2, sizeof(buf2), fmt, min, max);
     93   EXPECT_EQ(len, strlen(buf));
     94   EXPECT_EQ(0, strcmp(buf, buf2));
     95 }
     96 
     97 TEST(Printf, MinMax) {
     98   TestMinMax<int>("%d-%d", INT_MIN, INT_MAX);  // NOLINT
     99   TestMinMax<long>("%zd-%zd", LONG_MIN, LONG_MAX);  // NOLINT
    100   TestMinMax<unsigned>("%u-%u", 0, UINT_MAX);  // NOLINT
    101   TestMinMax<unsigned long>("%zu-%zu", 0, ULONG_MAX);  // NOLINT
    102   TestMinMax<unsigned>("%x-%x", 0, UINT_MAX);  // NOLINT
    103   TestMinMax<unsigned long>("%zx-%zx", 0, ULONG_MAX);  // NOLINT
    104 }
    105 
    106 }  // namespace __tsan
    107