15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2011 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
52a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include <limits>
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <sstream>
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <string>
85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/debug/stack_trace.h"
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/logging.h"
1158e6fbe4ee35d65e14b626c557d37565bf8ad179Ben Murdoch#include "base/process/kill.h"
1258e6fbe4ee35d65e14b626c557d37565bf8ad179Ben Murdoch#include "base/process/process_handle.h"
132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "base/test/test_timeouts.h"
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "testing/gtest/include/gtest/gtest.h"
152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "testing/multiprocess_func_list.h"
162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#if defined(OS_POSIX) && !defined(OS_ANDROID) && !defined(OS_IOS)
182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "base/test/multiprocess_test.h"
192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#endif
205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace base {
225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace debug {
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#if defined(OS_POSIX) && !defined(OS_ANDROID) && !defined(OS_IOS)
252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)typedef MultiProcessTest StackTraceTest;
262a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#else
272a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)typedef testing::Test StackTraceTest;
282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#endif
292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Note: On Linux, this test currently only fully works on Debug builds.
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// See comments in the #ifdef soup if you intend to change this.
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_WIN)
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Always fails on Windows: crbug.com/32070
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define MAYBE_OutputToStream DISABLED_OutputToStream
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define MAYBE_OutputToStream OutputToStream
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
38a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch#if !defined(__UCLIBC__)
392a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)TEST_F(StackTraceTest, MAYBE_OutputToStream) {
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  StackTrace trace;
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Dump the trace into a string.
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::ostringstream os;
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  trace.OutputToStream(&os);
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string backtrace_message = os.str();
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // ToString() should produce the same output.
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_EQ(backtrace_message, trace.ToString());
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_POSIX) && !defined(OS_MACOSX) && NDEBUG
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Stack traces require an extra data table that bloats our binaries,
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // so they're turned off for release builds.  We stop the test here,
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // at least letting us verify that the calls don't crash.
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return;
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif  // defined(OS_POSIX) && !defined(OS_MACOSX) && NDEBUG
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  size_t frames_found = 0;
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  trace.Addresses(&frames_found);
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ASSERT_GE(frames_found, 5u) <<
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      "No stack frames found.  Skipping rest of test.";
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Check if the output has symbol initialization warning.  If it does, fail.
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ASSERT_EQ(backtrace_message.find("Dumping unresolved backtrace"),
645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            std::string::npos) <<
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      "Unable to resolve symbols.  Skipping rest of test.";
665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_MACOSX)
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if 0
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Disabled due to -fvisibility=hidden in build config.
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Symbol resolution via the backtrace_symbol function does not work well
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // in OS X.
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // See this thread:
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //    http://lists.apple.com/archives/darwin-dev/2009/Mar/msg00111.html
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Just check instead that we find our way back to the "start" symbol
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // which should be the first symbol in the trace.
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // TODO(port): Find a more reliable way to resolve symbols.
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Expect to at least find main.
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_TRUE(backtrace_message.find("start") != std::string::npos)
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      << "Expected to find start in backtrace:\n"
855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      << backtrace_message;
865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#elif defined(USE_SYMBOLIZE)
895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This branch is for gcc-compiled code, but not Mac due to the
905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // above #if.
915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Expect a demangled symbol.
925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_TRUE(backtrace_message.find("testing::Test::Run()") !=
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)              std::string::npos)
945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      << "Expected a demangled symbol in backtrace:\n"
955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      << backtrace_message;
965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#elif 0
985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This is the fall-through case; it used to cover Windows.
995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // But it's disabled because of varying buildbot configs;
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // some lack symbols.
1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Expect to at least find main.
1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_TRUE(backtrace_message.find("main") != std::string::npos)
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      << "Expected to find main in backtrace:\n"
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      << backtrace_message;
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_WIN)
1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// MSVC doesn't allow the use of C99's __func__ within C++, so we fake it with
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// MSVC's __FUNCTION__ macro.
1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define __func__ __FUNCTION__
1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Expect to find this function as well.
1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Note: This will fail if not linked with -rdynamic (aka -export_dynamic)
1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EXPECT_TRUE(backtrace_message.find(__func__) != std::string::npos)
1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      << "Expected to find " << __func__ << " in backtrace:\n"
1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      << backtrace_message;
1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif  // define(OS_MACOSX)
1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// The test is used for manual testing, e.g., to see the raw output.
1232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)TEST_F(StackTraceTest, DebugOutputToStream) {
1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  StackTrace trace;
1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::ostringstream os;
1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  trace.OutputToStream(&os);
1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  VLOG(1) << os.str();
1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// The test is used for manual testing, e.g., to see the raw output.
1312a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)TEST_F(StackTraceTest, DebugPrintBacktrace) {
132424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)  StackTrace().Print();
1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
134a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch#endif  // !defined(__UCLIBC__)
1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1362a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#if defined(OS_POSIX) && !defined(OS_ANDROID)
1372a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#if !defined(OS_IOS)
1382a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)MULTIPROCESS_TEST_MAIN(MismatchedMallocChildProcess) {
1392a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  char* pointer = new char[10];
1402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  delete pointer;
1412a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  return 2;
1422a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
1432a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Regression test for StackDumpingSignalHandler async-signal unsafety.
1452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Combined with tcmalloc's debugallocation, that signal handler
1462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// and e.g. mismatched new[]/delete would cause a hang because
1472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// of re-entering malloc.
1482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)TEST_F(StackTraceTest, AsyncSignalUnsafeSignalHandlerHang) {
149a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  ProcessHandle child = SpawnChild("MismatchedMallocChildProcess");
1502a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ASSERT_NE(kNullProcessHandle, child);
1512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ASSERT_TRUE(WaitForSingleProcess(child, TestTimeouts::action_timeout()));
1522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
1532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#endif  // !defined(OS_IOS)
1542a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1552a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)namespace {
1562a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)std::string itoa_r_wrapper(intptr_t i, size_t sz, int base, size_t padding) {
1582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  char buffer[1024];
1592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  CHECK_LE(sz, sizeof(buffer));
1602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  char* result = internal::itoa_r(i, buffer, sz, base, padding);
1622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_TRUE(result);
1632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  return std::string(buffer);
1642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
1652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}  // namespace
1672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)TEST_F(StackTraceTest, itoa_r) {
1692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("0", itoa_r_wrapper(0, 128, 10, 0));
1702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("-1", itoa_r_wrapper(-1, 128, 10, 0));
1712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // Test edge cases.
1732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (sizeof(intptr_t) == 4) {
1742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    EXPECT_EQ("ffffffff", itoa_r_wrapper(-1, 128, 16, 0));
1752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    EXPECT_EQ("-2147483648",
1762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)              itoa_r_wrapper(std::numeric_limits<intptr_t>::min(), 128, 10, 0));
1772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    EXPECT_EQ("2147483647",
1782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)              itoa_r_wrapper(std::numeric_limits<intptr_t>::max(), 128, 10, 0));
1792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    EXPECT_EQ("80000000",
1812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)              itoa_r_wrapper(std::numeric_limits<intptr_t>::min(), 128, 16, 0));
1822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    EXPECT_EQ("7fffffff",
1832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)              itoa_r_wrapper(std::numeric_limits<intptr_t>::max(), 128, 16, 0));
1842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  } else if (sizeof(intptr_t) == 8) {
1852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    EXPECT_EQ("ffffffffffffffff", itoa_r_wrapper(-1, 128, 16, 0));
1862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    EXPECT_EQ("-9223372036854775808",
1872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)              itoa_r_wrapper(std::numeric_limits<intptr_t>::min(), 128, 10, 0));
1882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    EXPECT_EQ("9223372036854775807",
1892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)              itoa_r_wrapper(std::numeric_limits<intptr_t>::max(), 128, 10, 0));
1902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1912a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    EXPECT_EQ("8000000000000000",
1922a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)              itoa_r_wrapper(std::numeric_limits<intptr_t>::min(), 128, 16, 0));
1932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    EXPECT_EQ("7fffffffffffffff",
1942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)              itoa_r_wrapper(std::numeric_limits<intptr_t>::max(), 128, 16, 0));
1952a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  } else {
1962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    ADD_FAILURE() << "Missing test case for your size of intptr_t ("
1972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                  << sizeof(intptr_t) << ")";
1982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  }
1992a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
2002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // Test hex output.
2012a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("688", itoa_r_wrapper(0x688, 128, 16, 0));
2022a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("deadbeef", itoa_r_wrapper(0xdeadbeef, 128, 16, 0));
2032a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
2042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // Check that itoa_r respects passed buffer size limit.
2052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  char buffer[1024];
2062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_TRUE(internal::itoa_r(0xdeadbeef, buffer, 10, 16, 0));
2072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_TRUE(internal::itoa_r(0xdeadbeef, buffer, 9, 16, 0));
2082a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_FALSE(internal::itoa_r(0xdeadbeef, buffer, 8, 16, 0));
2092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_FALSE(internal::itoa_r(0xdeadbeef, buffer, 7, 16, 0));
2102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_TRUE(internal::itoa_r(0xbeef, buffer, 5, 16, 4));
2112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_FALSE(internal::itoa_r(0xbeef, buffer, 5, 16, 5));
2122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_FALSE(internal::itoa_r(0xbeef, buffer, 5, 16, 6));
2132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
2142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // Test padding.
2152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("1", itoa_r_wrapper(1, 128, 10, 0));
2162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("1", itoa_r_wrapper(1, 128, 10, 1));
2172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("01", itoa_r_wrapper(1, 128, 10, 2));
2182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("001", itoa_r_wrapper(1, 128, 10, 3));
2192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("0001", itoa_r_wrapper(1, 128, 10, 4));
2202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("00001", itoa_r_wrapper(1, 128, 10, 5));
2212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("688", itoa_r_wrapper(0x688, 128, 16, 0));
2222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("688", itoa_r_wrapper(0x688, 128, 16, 1));
2232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("688", itoa_r_wrapper(0x688, 128, 16, 2));
2242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("688", itoa_r_wrapper(0x688, 128, 16, 3));
2252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("0688", itoa_r_wrapper(0x688, 128, 16, 4));
2262a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  EXPECT_EQ("00688", itoa_r_wrapper(0x688, 128, 16, 5));
2272a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}
2282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#endif  // defined(OS_POSIX) && !defined(OS_ANDROID)
2292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
2305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace debug
2315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace base
232