Home | History | Annotate | Download | only in tests
      1 //===-- sanitizer_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 // Tests for sanitizer_printf.cc
     11 //
     12 //===----------------------------------------------------------------------===//
     13 #include "sanitizer_common/sanitizer_common.h"
     14 #include "sanitizer_common/sanitizer_libc.h"
     15 #include "gtest/gtest.h"
     16 
     17 #include <string.h>
     18 #include <limits.h>
     19 
     20 namespace __sanitizer {
     21 
     22 TEST(Printf, Basic) {
     23   char buf[1024];
     24   uptr len = internal_snprintf(buf, sizeof(buf),
     25       "a%db%zdc%ue%zuf%xh%zxq%pe%sr",
     26       (int)-1, (long)-2, // NOLINT
     27       (unsigned)-4, (unsigned long)5, // NOLINT
     28       (unsigned)10, (unsigned long)11, // NOLINT
     29       (void*)0x123, "_string_");
     30   EXPECT_EQ(len, strlen(buf));
     31   void *ptr;
     32   if (sizeof(ptr) == 4) {
     33     EXPECT_STREQ("a-1b-2c4294967292e5fahbq"
     34                  "0x00000123e_string_r", buf);
     35   } else {
     36     EXPECT_STREQ("a-1b-2c4294967292e5fahbq"
     37                  "0x000000000123e_string_r", buf);
     38   }
     39 }
     40 
     41 TEST(Printf, OverflowStr) {
     42   char buf[] = "123456789";
     43   uptr len = internal_snprintf(buf, 4, "%s", "abcdef");  // NOLINT
     44   EXPECT_EQ(len, (uptr)6);
     45   EXPECT_STREQ("abc", buf);
     46   EXPECT_EQ(buf[3], 0);
     47   EXPECT_EQ(buf[4], '5');
     48   EXPECT_EQ(buf[5], '6');
     49   EXPECT_EQ(buf[6], '7');
     50   EXPECT_EQ(buf[7], '8');
     51   EXPECT_EQ(buf[8], '9');
     52   EXPECT_EQ(buf[9], 0);
     53 }
     54 
     55 TEST(Printf, OverflowInt) {
     56   char buf[] = "123456789";
     57   internal_snprintf(buf, 4, "%d", -123456789);  // NOLINT
     58   EXPECT_STREQ("-12", buf);
     59   EXPECT_EQ(buf[3], 0);
     60   EXPECT_EQ(buf[4], '5');
     61   EXPECT_EQ(buf[5], '6');
     62   EXPECT_EQ(buf[6], '7');
     63   EXPECT_EQ(buf[7], '8');
     64   EXPECT_EQ(buf[8], '9');
     65   EXPECT_EQ(buf[9], 0);
     66 }
     67 
     68 TEST(Printf, OverflowUint) {
     69   char buf[] = "123456789";
     70   uptr val;
     71   if (sizeof(val) == 4) {
     72     val = (uptr)0x12345678;
     73   } else {
     74     val = (uptr)0x123456789ULL;
     75   }
     76   internal_snprintf(buf, 4, "a%zx", val);  // NOLINT
     77   EXPECT_STREQ("a12", buf);
     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 TEST(Printf, OverflowPtr) {
     88   char buf[] = "123456789";
     89   void *p;
     90   if (sizeof(p) == 4) {
     91     p = (void*)0x1234567;
     92   } else {
     93     p = (void*)0x123456789ULL;
     94   }
     95   internal_snprintf(buf, 4, "%p", p);  // NOLINT
     96   EXPECT_STREQ("0x0", buf);
     97   EXPECT_EQ(buf[3], 0);
     98   EXPECT_EQ(buf[4], '5');
     99   EXPECT_EQ(buf[5], '6');
    100   EXPECT_EQ(buf[6], '7');
    101   EXPECT_EQ(buf[7], '8');
    102   EXPECT_EQ(buf[8], '9');
    103   EXPECT_EQ(buf[9], 0);
    104 }
    105 
    106 #if defined(_WIN32)
    107 // Oh well, MSVS headers don't define snprintf.
    108 # define snprintf _snprintf
    109 #endif
    110 
    111 template<typename T>
    112 static void TestAgainstLibc(const char *fmt, T arg1, T arg2) {
    113   char buf[1024];
    114   uptr len = internal_snprintf(buf, sizeof(buf), fmt, arg1, arg2);
    115   char buf2[1024];
    116   snprintf(buf2, sizeof(buf2), fmt, arg1, arg2);
    117   EXPECT_EQ(len, strlen(buf));
    118   EXPECT_STREQ(buf2, buf);
    119 }
    120 
    121 TEST(Printf, MinMax) {
    122   TestAgainstLibc<int>("%d-%d", INT_MIN, INT_MAX);  // NOLINT
    123   TestAgainstLibc<unsigned>("%u-%u", 0, UINT_MAX);  // NOLINT
    124   TestAgainstLibc<unsigned>("%x-%x", 0, UINT_MAX);  // NOLINT
    125 #if !defined(_WIN32)
    126   // %z* format doesn't seem to be supported by MSVS.
    127   TestAgainstLibc<long>("%zd-%zd", LONG_MIN, LONG_MAX);  // NOLINT
    128   TestAgainstLibc<unsigned long>("%zu-%zu", 0, ULONG_MAX);  // NOLINT
    129   TestAgainstLibc<unsigned long>("%zx-%zx", 0, ULONG_MAX);  // NOLINT
    130 #endif
    131 }
    132 
    133 TEST(Printf, Padding) {
    134   TestAgainstLibc<int>("%3d - %3d", 1, 0);
    135   TestAgainstLibc<int>("%3d - %3d", -1, 123);
    136   TestAgainstLibc<int>("%3d - %3d", -1, -123);
    137   TestAgainstLibc<int>("%3d - %3d", 12, 1234);
    138   TestAgainstLibc<int>("%3d - %3d", -12, -1234);
    139   TestAgainstLibc<int>("%03d - %03d", 1, 0);
    140   TestAgainstLibc<int>("%03d - %03d", -1, 123);
    141   TestAgainstLibc<int>("%03d - %03d", -1, -123);
    142   TestAgainstLibc<int>("%03d - %03d", 12, 1234);
    143   TestAgainstLibc<int>("%03d - %03d", -12, -1234);
    144 }
    145 
    146 TEST(Printf, Precision) {
    147   char buf[1024];
    148   uptr len = internal_snprintf(buf, sizeof(buf), "%.*s", 3, "12345");
    149   EXPECT_EQ(3U, len);
    150   EXPECT_STREQ("123", buf);
    151   len = internal_snprintf(buf, sizeof(buf), "%.*s", 6, "12345");
    152   EXPECT_EQ(5U, len);
    153   EXPECT_STREQ("12345", buf);
    154 }
    155 
    156 }  // namespace __sanitizer
    157