Replaced calls to functions that msvc consider deprecated. Used
authorchristian.plesner.hansen@gmail.com <christian.plesner.hansen@gmail.com@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Thu, 11 Sep 2008 14:34:48 +0000 (14:34 +0000)
committerchristian.plesner.hansen@gmail.com <christian.plesner.hansen@gmail.com@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Thu, 11 Sep 2008 14:34:48 +0000 (14:34 +0000)
Vector<...> in more places to be sure that buffers have a length
associated with them.

Review URL: http://codereview.chromium.org/1940

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@283 ce2b1a6d-e550-0410-aec6-3dcde31c8c00

23 files changed:
SConstruct
src/counters.cc
src/counters.h
src/disasm-ia32.cc
src/disasm.h
src/disassembler.cc
src/execution.cc
src/flags.cc
src/log.cc
src/objects.cc
src/platform-linux.cc
src/platform-win32.cc
src/platform.h
src/prettyprinter.cc
src/serialize.cc
src/string-stream.cc
src/top.cc
src/utils.cc
src/utils.h
test/cctest/cctest.cc
test/cctest/test-compiler.cc
test/cctest/test-debug.cc
test/cctest/test-utils.cc

index a2bed5652c1c2f571c8a61be3a30f5f69feadfe0..84f6b091e24ec59e95d0ad9c943360e107a4b124 100644 (file)
@@ -66,9 +66,7 @@ LIBRARY_FLAGS = {
       'WARNINGFLAGS': ['/W3', '/WX', '/wd4355', '/wd4800'],
       'CCFLAGS':      ['$DIALECTFLAGS', '$WARNINGFLAGS'],
       'CXXFLAGS':     ['$CCFLAGS', '/GR-', '/Gy'],
-      'CPPDEFINES':   ['WIN32', '_CRT_SECURE_NO_DEPRECATE',
-          '_CRT_NONSTDC_NO_DEPRECATE', '_USE_32BIT_TIME_T',
-          'PCRE_STATIC'],
+      'CPPDEFINES':   ['WIN32', '_USE_32BIT_TIME_T', 'PCRE_STATIC'],
       'LINKFLAGS':    ['/NOLOGO', '/MACHINE:X86', '/INCREMENTAL:NO',
           '/NXCOMPAT', '/IGNORE:4221'],
       'ARFLAGS':      ['/NOLOGO'],
index 3baad2943757ff61f1bf9de0c32e9949547ab95a..b828874aa7644596da3aef8df36a2d51d26ee8a6 100644 (file)
@@ -39,9 +39,9 @@ StatsCounterTimer::StatsCounterTimer(const wchar_t* name)
     stop_time_(0) {  // initialize to avoid compiler complaints
   int len = wcslen(name);
   // we prepend the name with 'c.' to indicate that it is a counter.
-  name_ = NewArray<wchar_t>(len+3);
-  wcscpy(name_, L"t:");
-  wcscpy(&name_[2], name);
+  name_ = Vector<wchar_t>::New(len+3);
+  OS::WcsCpy(name_, L"t:");
+  OS::WcsCpy(name_ + 2, name);
 }
 
 // Start the timer.
index 6dd9e94f362bb26a40b254e38df302fc99d17a6c..1225a70ebe2e8ba464e7bcc642761731395318bd 100644 (file)
@@ -91,13 +91,13 @@ class StatsCounter BASE_EMBEDDED {
       id_(id) {
     int len = wcslen(name);
     // we prepend the name with 'c:' to indicate that it is a counter.
-    name_ = NewArray<wchar_t>(len+3);
-    wcscpy(name_, L"c:");
-    wcscpy(&name_[2], name);
+    name_ = Vector<wchar_t>::New(len+3);
+    OS::WcsCpy(name_, L"c:");
+    OS::WcsCpy(name_ + 2, name);
   };
 
   ~StatsCounter() {
-    DeleteArray(name_);
+    name_.Dispose();
   }
 
   // Sets the counter to a specific value.
@@ -159,11 +159,11 @@ class StatsCounter BASE_EMBEDDED {
     if (lookup_done_)
       return ptr_;
     lookup_done_ = true;
-    ptr_ = StatsTable::FindLocation(name_);
+    ptr_ = StatsTable::FindLocation(name_.start());
     return ptr_;
   }
 
-  wchar_t* name_;
+  Vector<wchar_t> name_;
   bool lookup_done_;
   int* ptr_;
   int id_;
index ac12e1f4cb68d6252a996471482d4293655f5b0d..70c7baaf5ae653219ebab0a374c46d42261b7971 100644 (file)
@@ -233,11 +233,11 @@ class DisassemblerIA32 {
 
   // Writes one disassembled instruction into 'buffer' (0-terminated).
   // Returns the length of the disassembled machine instruction in bytes.
-  int InstructionDecode(char* buffer, const int buffer_size, byte* instruction);
+  int InstructionDecode(v8::internal::Vector<char> buffer, byte* instruction);
 
  private:
   const NameConverter& converter_;
-  char tmp_buffer_[128];
+  v8::internal::EmbeddedVector<char, 128> tmp_buffer_;
   unsigned int tmp_buffer_pos_;
   bool abort_on_unimplemented_;
 
@@ -307,15 +307,10 @@ class DisassemblerIA32 {
 
 
 void DisassemblerIA32::AppendToBuffer(const char* format, ...) {
-  char* str = tmp_buffer_ + tmp_buffer_pos_;
-  int size = (sizeof tmp_buffer_) - tmp_buffer_pos_;
+  v8::internal::Vector<char> buf = tmp_buffer_ + tmp_buffer_pos_;
   va_list args;
   va_start(args, format);
-#ifdef WIN32
-  int result = _vsnprintf(str, size, format, args);
-#else
-  int result = vsnprintf(str, size, format, args);
-#endif
+  int result = v8::internal::OS::VSNPrintF(buf, format, args);
   va_end(args);
   tmp_buffer_pos_ += result;
 }
@@ -706,8 +701,7 @@ static const char* F0Mnem(byte f0byte) {
 
 
 // Disassembled instruction '*instr' and writes it intro 'out_buffer'.
-int DisassemblerIA32::InstructionDecode(char* out_buffer,
-                                        const int out_buffer_size,
+int DisassemblerIA32::InstructionDecode(v8::internal::Vector<char> out_buffer,
                                         byte* instr) {
   tmp_buffer_pos_ = 0;  // starting to write as position 0
   byte* data = instr;
@@ -1040,20 +1034,17 @@ int DisassemblerIA32::InstructionDecode(char* out_buffer,
   // Instruction bytes.
   for (byte* bp = instr; bp < data; bp++) {
     outp += v8::internal::OS::SNPrintF(out_buffer + outp,
-                                       out_buffer_size - outp,
                                        "%02x",
                                        *bp);
   }
   for (int i = 6 - instr_len; i >= 0; i--) {
     outp += v8::internal::OS::SNPrintF(out_buffer + outp,
-                                       out_buffer_size - outp,
                                        "  ");
   }
 
   outp += v8::internal::OS::SNPrintF(out_buffer + outp,
-                                     out_buffer_size - outp,
                                      " %s",
-                                     tmp_buffer_);
+                                     tmp_buffer_.start());
   return instr_len;
 }
 
@@ -1072,13 +1063,9 @@ static const char* xmm_regs[8] = {
 
 
 const char* NameConverter::NameOfAddress(byte* addr) const {
-  static char tmp_buffer[32];
-#ifdef WIN32
-  _snprintf(tmp_buffer, sizeof tmp_buffer, "%p", addr);
-#else
-  snprintf(tmp_buffer, sizeof tmp_buffer, "%p", addr);
-#endif
-  return tmp_buffer;
+  v8::internal::EmbeddedVector<char, 32> tmp_buffer;
+  v8::internal::OS::SNPrintF(tmp_buffer, "%p", addr);
+  return tmp_buffer.start();
 }
 
 
@@ -1120,11 +1107,10 @@ Disassembler::Disassembler(const NameConverter& converter)
 Disassembler::~Disassembler() {}
 
 
-int Disassembler::InstructionDecode(char* buffer,
-                                    const int buffer_size,
+int Disassembler::InstructionDecode(v8::internal::Vector<char> buffer,
                                     byte* instruction) {
   DisassemblerIA32 d(converter_, false /*do not crash if unimplemented*/);
-  return d.InstructionDecode(buffer, buffer_size, instruction);
+  return d.InstructionDecode(buffer, instruction);
 }
 
 
@@ -1135,10 +1121,10 @@ int Disassembler::ConstantPoolSizeAt(byte* instruction) { return -1; }
 /*static*/ void Disassembler::Disassemble(FILE* f, byte* begin, byte* end) {
   Disassembler d;
   for (byte* pc = begin; pc < end;) {
-    char buffer[128];
+    v8::internal::EmbeddedVector<char, 128> buffer;
     buffer[0] = '\0';
     byte* prev_pc = pc;
-    pc += d.InstructionDecode(buffer, sizeof buffer, pc);
+    pc += d.InstructionDecode(buffer, pc);
     fprintf(f, "%p", prev_pc);
     fprintf(f, "    ");
 
@@ -1148,7 +1134,7 @@ int Disassembler::ConstantPoolSizeAt(byte* instruction) { return -1; }
     for (int i = 6 - (pc - prev_pc); i >= 0; i--) {
       fprintf(f, "  ");
     }
-    fprintf(f, "  %s\n", buffer);
+    fprintf(f, "  %s\n", buffer.start());
   }
 }
 
index f590b281d8daa7d67967073a0a091c79c5169102..1b72ee1a212a0037768bd9069ae07b7b6e12fe98 100644 (file)
@@ -59,7 +59,7 @@ class Disassembler {
 
   // Writes one disassembled instruction into 'buffer' (0-terminated).
   // Returns the length of the disassembled machine instruction in bytes.
-  int InstructionDecode(char* buffer, const int buffer_size, byte* instruction);
+  int InstructionDecode(v8::internal::Vector<char> buffer, byte* instruction);
 
   // Returns -1 if instruction does not mark the beginning of a constant pool,
   // or the number of entries in the constant pool beginning here.
index 635440dddbd9f1ebe8deeb3643c17eebabd3801a..6363008b2f40e89071d4f8bc6240be8ddabaf003 100644 (file)
@@ -63,20 +63,20 @@ class V8NameConverter: public disasm::NameConverter {
 
 
 const char* V8NameConverter::NameOfAddress(byte* pc) const {
-  static char buffer[128];
+  static v8::internal::EmbeddedVector<char, 128> buffer;
 
   const char* name = Builtins::Lookup(pc);
   if (name != NULL) {
-    OS::SNPrintF(buffer, sizeof buffer, "%s  (%p)", name, pc);
-    return buffer;
+    OS::SNPrintF(buffer, "%s  (%p)", name, pc);
+    return buffer.start();
   }
 
   if (code_ != NULL) {
     int offs = pc - code_->instruction_start();
     // print as code offset, if it seems reasonable
     if (0 <= offs && offs < code_->instruction_size()) {
-      OS::SNPrintF(buffer, sizeof buffer, "%d  (%p)", offs, pc);
-      return buffer;
+      OS::SNPrintF(buffer, "%d  (%p)", offs, pc);
+      return buffer.start();
     }
   }
 
@@ -110,8 +110,8 @@ static int DecodeIt(FILE* f,
   AssertNoAllocation no_alloc;
   ExternalReferenceEncoder ref_encoder;
 
-  char decode_buffer[128];
-  char out_buffer[kOutBufferSize];
+  v8::internal::EmbeddedVector<char, 128> decode_buffer;
+  v8::internal::EmbeddedVector<char, kOutBufferSize> out_buffer;
   byte* pc = begin;
   disasm::Disassembler d(converter);
   RelocIterator* it = NULL;
@@ -127,7 +127,6 @@ static int DecodeIt(FILE* f,
     byte* prev_pc = pc;
     if (constants > 0) {
       OS::SNPrintF(decode_buffer,
-                   sizeof(decode_buffer),
                    "%08x       constant",
                    *reinterpret_cast<int32_t*>(pc));
       constants--;
@@ -136,14 +135,13 @@ static int DecodeIt(FILE* f,
       int num_const = d.ConstantPoolSizeAt(pc);
       if (num_const >= 0) {
         OS::SNPrintF(decode_buffer,
-                     sizeof(decode_buffer),
                      "%08x       constant pool begin",
                      *reinterpret_cast<int32_t*>(pc));
         constants = num_const;
         pc += 4;
       } else {
         decode_buffer[0] = '\0';
-        pc += d.InstructionDecode(decode_buffer, sizeof decode_buffer, pc);
+        pc += d.InstructionDecode(decode_buffer, pc);
       }
     }
 
@@ -167,7 +165,7 @@ static int DecodeIt(FILE* f,
       }
     }
 
-    StringBuilder out(out_buffer, sizeof(out_buffer));
+    StringBuilder out(out_buffer.start(), out_buffer.length());
 
     // Comments.
     for (int i = 0; i < comments.length(); i++) {
@@ -182,7 +180,7 @@ static int DecodeIt(FILE* f,
     out.AddFormatted("%p  %4d  ", prev_pc, prev_pc - begin);
 
     // Instruction.
-    out.AddFormatted("%s", decode_buffer);
+    out.AddFormatted("%s", decode_buffer.start());
 
     // Print all the reloc info for this instruction which are not comments.
     for (int i = 0; i < pcs.length(); i++) {
index ce2259e0c7644671f75e0a803cd37a6e2766fbb1..daf8baba3a4227c84029c8e30710084a64edd39f 100644 (file)
@@ -587,10 +587,10 @@ v8::Handle<v8::Value> LoadExtension::Load(const v8::Arguments& args) {
     static const size_t kErrorPrefixLength = 25;  // strlen is not constant
     ASSERT(strlen(kErrorPrefix) == kErrorPrefixLength);
     static const int kMaxErrorLength = kMaxPathLength + kErrorPrefixLength;
-    char error_buffer[kMaxErrorLength + 1];
-    OS::SNPrintF(error_buffer, kMaxErrorLength, "%s%s",
-                 kErrorPrefix, file_name_buffer);
-    v8::Handle<v8::String> error = v8::String::New(error_buffer);
+    EmbeddedVector<char, kMaxErrorLength + 1> error_buffer;
+    OS::SNPrintF(error_buffer, "%s%s", kErrorPrefix, file_name_buffer);
+    v8::Handle<v8::String> error =
+        v8::String::New(error_buffer.start(), error_buffer.length());
     v8::ThrowException(v8::Exception::Error(error));
     return result;
   }
index 1f8413cd3badab6afd35b58779002a5d5f69aebc..b8a9e99d87d722c6a3530244ed7a9dbec286565f 100644 (file)
@@ -134,33 +134,33 @@ static const char* Type2String(Flag::Type type) {
 
 
 static char* ToString(Flag::Type type, FlagValue* variable) {
-  char* value = NULL;
+  Vector<char> value;
   switch (type) {
     case Flag::BOOL:
-      value = NewArray<char>(6);
-      OS::SNPrintF(value, 6, "%s", (variable->b ? "true" : "false"));
+      value = Vector<char>::New(6);
+      OS::SNPrintF(value, "%s", (variable->b ? "true" : "false"));
       break;
     case Flag::INT:
-      value = NewArray<char>(12);
-      OS::SNPrintF(value, 12, "%d", variable->i);
+      value = Vector<char>::New(12);
+      OS::SNPrintF(value, "%d", variable->i);
       break;
     case Flag::FLOAT:
-      value = NewArray<char>(20);
-      OS::SNPrintF(value, 20, "%f", variable->f);
+      value = Vector<char>::New(20);
+      OS::SNPrintF(value, "%f", variable->f);
       break;
     case Flag::STRING:
       if (variable->s) {
         int length = strlen(variable->s) + 1;
-        value = NewArray<char>(length);
-        OS::SNPrintF(value, length, "%s", variable->s);
+        value = Vector<char>::New(length);
+        OS::SNPrintF(value, "%s", variable->s);
       } else {
-        value = NewArray<char>(5);
-        OS::SNPrintF(value, 5, "NULL");
+        value = Vector<char>::New(5);
+        OS::SNPrintF(value, "NULL");
       }
       break;
   }
-  ASSERT(value != NULL);
-  return value;
+  ASSERT(!value.is_empty());
+  return value.start();
 }
 
 
@@ -198,17 +198,17 @@ List<char *>* FlagList::argv() {
   List<char *>* args = new List<char*>(8);
   for (Flag* f = list_; f != NULL; f = f->next()) {
     if (!f->IsDefault()) {
-      char* cmdline_flag;
+      Vector<char> cmdline_flag;
       if (f->type() != Flag::BOOL || *(f->bool_variable())) {
         int length = strlen(f->name()) + 2 + 1;
-        cmdline_flag = NewArray<char>(length);
-        OS::SNPrintF(cmdline_flag, length, "--%s", f->name());
+        cmdline_flag = Vector<char>::New(length);
+        OS::SNPrintF(cmdline_flag, "--%s", f->name());
       } else {
         int length = strlen(f->name()) + 4 + 1;
-        cmdline_flag = NewArray<char>(length);
-        OS::SNPrintF(cmdline_flag, length, "--no%s", f->name());
+        cmdline_flag = Vector<char>::New(length);
+        OS::SNPrintF(cmdline_flag, "--no%s", f->name());
       }
-      args->Add(cmdline_flag);
+      args->Add(cmdline_flag.start());
       if (f->type() != Flag::BOOL) {
         args->Add(f->StringValue());
       }
index 92d18d0b8091e4bd3396d37cf358d31954d41e99..c650d4a1013a9ca06a64d90d8a70f232a1e0befd 100644 (file)
@@ -702,7 +702,7 @@ bool Logger::Setup() {
     if (strcmp(FLAG_logfile, "-") == 0) {
       logfile_ = stdout;
     } else {
-      logfile_ = fopen(FLAG_logfile, "w");
+      logfile_ = OS::FOpen(FLAG_logfile, "w");
     }
     mutex_ = OS::CreateMutex();
   }
index 46ac8f53e821ecb31c892c19976054fbf2ab1e22..6312e4e4083a76ef0c82e317c86373d29a17401f 100644 (file)
@@ -893,9 +893,9 @@ void HeapNumber::HeapNumberPrint(StringStream* accumulator) {
   // buffer that is plenty big enough for any floating point number, then
   // print that using vsnprintf (which may truncate but never allocate if
   // there is no more space in the buffer).
-  char buffer[100];
-  OS::SNPrintF(buffer, sizeof(buffer), "%.16g", Number());
-  accumulator->Add("%s", buffer);
+  EmbeddedVector<char, 100> buffer;
+  OS::SNPrintF(buffer, "%.16g", Number());
+  accumulator->Add("%s", buffer.start());
 }
 
 
index ba72768a7ceb02a156e04a13a4178bd3ac4a9a57..9589bf937388ab7fcc19caf68ee50dbc0a561947 100644 (file)
@@ -126,6 +126,11 @@ double OS::LocalTimeOffset() {
 }
 
 
+FILE* OS::FOpen(const char* path, const char* mode) {
+  return fopen(path, mode);
+}
+
+
 void OS::Print(const char* format, ...) {
   va_list args;
   va_start(args, format);
@@ -152,19 +157,21 @@ void OS::VPrintError(const char* format, va_list args) {
 }
 
 
-int OS::SNPrintF(char* str, size_t size, const char* format, ...) {
+int OS::SNPrintF(Vector<char> str, const char* format, ...) {
   va_list args;
   va_start(args, format);
-  int result = VSNPrintF(str, size, format, args);
+  int result = VSNPrintF(str, format, args);
   va_end(args);
   return result;
 }
 
 
-int OS::VSNPrintF(char* str, size_t size, const char* format, va_list args) {
-  int n = vsnprintf(str, size, format, args);  // forward to linux.
-  if (n < 0 || static_cast<size_t>(n) >= size) {
-    str[size - 1] = '\0';
+int OS::VSNPrintF(Vector<char> str,
+                  const char* format,
+                  va_list args) {
+  int n = vsnprintf(str.start(), str.length(), format, args);
+  if (n < 0 || n >= str.length()) {
+    str[str.length() - 1] = '\0';
     return -1;
   } else {
     return n;
@@ -172,6 +179,21 @@ int OS::VSNPrintF(char* str, size_t size, const char* format, va_list args) {
 }
 
 
+void OS::StrNCpy(Vector<char> dest, const char* src, size_t n) {
+  strncpy(dest.start(), src, n);
+}
+
+
+void OS::WcsCpy(Vector<wchar_t> dest, const wchar_t* src) {
+  wcscpy(dest.start(), src);
+}
+
+
+char *OS::StrDup(const char* str) {
+  return strdup(str);
+}
+
+
 double OS::nan_value() { return NAN; }
 
 // We keep the lowest and highest addresses mapped as a quick way of
@@ -341,7 +363,9 @@ int OS::StackWalk(OS::StackFrame* frames, int frames_size) {
     frames[i].address = addresses[i];
     // Format a text representation of the frame based on the information
     // available.
-    SNPrintF(frames[i].text, kStackWalkMaxTextLen, "%s", symbols[i]);
+    SNPrintF(MutableCStrVector(frames[i].text, kStackWalkMaxTextLen),
+             "%s",
+             symbols[i]);
     // Make sure line termination is in place.
     frames[i].text[kStackWalkMaxTextLen - 1] = '\0';
   }
index 60354659d281f6eaa95f44daacbf162dd2d6d866..d0d044fd6e3852186b521915ba501a900e5504b0 100644 (file)
@@ -156,14 +156,14 @@ int random() {
 // Case-insensitive string comparisons. Use stricmp() on Win32. Usually defined
 // in strings.h.
 int strcasecmp(const char* s1, const char* s2) {
-  return stricmp(s1, s2);
+  return _stricmp(s1, s2);
 }
 
 
 // Case-insensitive bounded string comparisons. Use stricmp() on Win32. Usually
 // defined in strings.h.
 int strncasecmp(const char* s1, const char* s2, int n) {
-  return strnicmp(s1, s2, n);
+  return _strnicmp(s1, s2, n);
 }
 
 namespace v8 { namespace internal {
@@ -341,9 +341,13 @@ void Time::TzSet() {
   }
 
   // Make standard and DST timezone names.
-  _snprintf(std_tz_name_, kTzNameSize, "%S", tzinfo_.StandardName);
+  OS::SNPrintF(Vector<char>(std_tz_name_, kTzNameSize),
+               "%S",
+               tzinfo_.StandardName);
   std_tz_name_[kTzNameSize - 1] = '\0';
-  _snprintf(dst_tz_name_, kTzNameSize, "%S", tzinfo_.DaylightName);
+  OS::SNPrintF(Vector<char>(dst_tz_name_, kTzNameSize),
+               "%S",
+               tzinfo_.DaylightName);
   dst_tz_name_[kTzNameSize - 1] = '\0';
 
   // If OS returned empty string or resource id (like "@tzres.dll,-211")
@@ -351,12 +355,14 @@ void Time::TzSet() {
   // To properly resolve the resource identifier requires a library load,
   // which is not possible in a sandbox.
   if (std_tz_name_[0] == '\0' || std_tz_name_[0] == '@') {
-    _snprintf(std_tz_name_, kTzNameSize - 1, "%s Standard Time",
-              GuessTimezoneNameFromBias(tzinfo_.Bias));
+    OS::SNPrintF(Vector<char>(std_tz_name_, kTzNameSize - 1),
+                 "%s Standard Time",
+                 GuessTimezoneNameFromBias(tzinfo_.Bias));
   }
   if (dst_tz_name_[0] == '\0' || dst_tz_name_[0] == '@') {
-    _snprintf(dst_tz_name_, kTzNameSize - 1, "%s Daylight Time",
-              GuessTimezoneNameFromBias(tzinfo_.Bias));
+    OS::SNPrintF(Vector<char>(dst_tz_name_, kTzNameSize - 1),
+                 "%s Daylight Time",
+                 GuessTimezoneNameFromBias(tzinfo_.Bias));
   }
 
   // Timezone information initialized.
@@ -607,10 +613,19 @@ static void VPrintHelper(FILE* stream, const char* format, va_list args) {
     // It is important to use safe print here in order to avoid
     // overflowing the buffer. We might truncate the output, but this
     // does not crash.
-    static const int kBufferSize = 4096;
-    char buffer[kBufferSize];
-    OS::VSNPrintF(buffer, kBufferSize, format, args);
-    OutputDebugStringA(buffer);
+    EmbeddedVector<char, 4096> buffer;
+    OS::VSNPrintF(buffer, format, args);
+    OutputDebugStringA(buffer.start());
+  }
+}
+
+
+FILE* OS::FOpen(const char* path, const char* mode) {
+  FILE* result;
+  if (fopen_s(&result, path, mode) == 0) {
+    return result;
+  } else {
+    return NULL;
   }
 }
 
@@ -643,24 +658,21 @@ void OS::VPrintError(const char* format, va_list args) {
 }
 
 
-int OS::SNPrintF(char* str, size_t size, const char* format, ...) {
+int OS::SNPrintF(Vector<char> str, const char* format, ...) {
   va_list args;
   va_start(args, format);
-  int result = VSNPrintF(str, size, format, args);
+  int result = VSNPrintF(str, format, args);
   va_end(args);
   return result;
 }
 
 
-int OS::VSNPrintF(char* str, size_t size, const char* format, va_list args) {
-  // Print formated output to string. The _vsnprintf function has been
-  // deprecated in MSVC. We need to define _CRT_NONSTDC_NO_DEPRECATE
-  // during compilation to use it anyway. Usually defined in stdio.h.
-  int n = _vsnprintf(str, size, format, args);
+int OS::VSNPrintF(Vector<char> str, const char* format, va_list args) {
+  int n = _vsnprintf_s(str.start(), str.length(), str.length(), format, args);
   // Make sure to zero-terminate the string if the output was
   // truncated or if there was an error.
-  if (n < 0 || static_cast<size_t>(n) >= size) {
-    str[size - 1] = '\0';
+  if (n < 0 || n >= str.length()) {
+    str[str.length() - 1] = '\0';
     return -1;
   } else {
     return n;
@@ -668,6 +680,23 @@ int OS::VSNPrintF(char* str, size_t size, const char* format, va_list args) {
 }
 
 
+void OS::StrNCpy(Vector<char> dest, const char* src, size_t n) {
+  int result = strncpy_s(dest.start(), dest.length(), src, n);
+  USE(result); ASSERT(result == 0);
+}
+
+
+void OS::WcsCpy(Vector<wchar_t> dest, const wchar_t* src) {
+  int result = wcscpy_s(dest.start(), dest.length(), src);
+  USE(result); ASSERT(result == 0);
+}
+
+
+char *OS::StrDup(const char* str) {
+  return _strdup(str);
+}
+
+
 // We keep the lowest and highest addresses mapped as a quick way of
 // determining that pointers are outside the heap (used mostly in assertions
 // and verification).  The estimate is conservative, ie, not all addresses in
@@ -1132,11 +1161,15 @@ int OS::StackWalk(OS::StackFrame* frames, int frames_size) {
       // Format a text representation of the frame based on the information
       // available.
       if (ok) {
-        SNPrintF(frames[frames_count].text, kStackWalkMaxTextLen, "%s %s:%d:%d",
+        SNPrintF(MutableCStrVector(frames[frames_count].text,
+                                   kStackWalkMaxTextLen),
+                 "%s %s:%d:%d",
                  symbol->Name, Line.FileName, Line.LineNumber,
                  line_displacement);
       } else {
-        SNPrintF(frames[frames_count].text, kStackWalkMaxTextLen, "%s",
+        SNPrintF(MutableCStrVector(frames[frames_count].text,
+                                   kStackWalkMaxTextLen),
+                 "%s",
                  symbol->Name);
       }
       // Make sure line termination is in place.
index 1cb42d26d4a1cf562df05ae6091597f20643800b..5bb7f200e085a2839e0b28bd7a88896dd77e3c22 100644 (file)
@@ -132,6 +132,8 @@ class OS {
   // Returns the daylight savings offset for the given time.
   static double DaylightSavingsOffset(double time);
 
+  static FILE* FOpen(const char* path, const char* mode);
+
   // Print output to console. This is mostly used for debugging output.
   // On platforms that has standard terminal output, the output
   // should go to stdout.
@@ -198,12 +200,15 @@ class OS {
 
   // Safe formatting print. Ensures that str is always null-terminated.
   // Returns the number of chars written, or -1 if output was truncated.
-  static int SNPrintF(char* str, size_t size, const char* format, ...);
-  static int VSNPrintF(char* str,
-                       size_t size,
+  static int SNPrintF(Vector<char> str, const char* format, ...);
+  static int VSNPrintF(Vector<char> str,
                        const char* format,
                        va_list args);
 
+  static void StrNCpy(Vector<char> dest, const char* src, size_t n);
+  static void WcsCpy(Vector<wchar_t> dest, const wchar_t* src);
+  static char* StrDup(const char* str);
+
   // Support for profiler.  Can do nothing, in which case ticks
   // occuring in shared libraries will not be properly accounted
   // for.
index 2f377d80335e8f6bd2aeb768994a4930ff4efdbb..fef270e9516efa14aedac5f68130e4ba5b86006d 100644 (file)
@@ -448,8 +448,9 @@ void PrettyPrinter::Print(const char* format, ...) {
   for (;;) {
     va_list arguments;
     va_start(arguments, format);
-    int available = size_ - pos_;
-    int n = OS::VSNPrintF(output_ + pos_, available, format, arguments);
+    int n = OS::VSNPrintF(Vector<char>(output_, size_) + pos_,
+                          format,
+                          arguments);
     va_end(arguments);
 
     if (n >= 0) {
@@ -648,10 +649,10 @@ void AstPrinter::PrintLiteralWithModeIndented(const char* info,
   if (var == NULL) {
     PrintLiteralIndented(info, value, true);
   } else {
-    char buf[256];
-    OS::SNPrintF(buf, sizeof(buf), "%s (mode = %s)", info,
+    EmbeddedVector<char, 256> buf;
+    OS::SNPrintF(buf, "%s (mode = %s)", info,
                  Variable::Mode2String(var->mode()));
-    PrintLiteralIndented(buf, value, true);
+    PrintLiteralIndented(buf.start(), value, true);
   }
 }
 
@@ -1019,10 +1020,10 @@ void AstPrinter::VisitUnaryOperation(UnaryOperation* node) {
 
 
 void AstPrinter::VisitCountOperation(CountOperation* node) {
-  char buf[128];
-  OS::SNPrintF(buf, sizeof(buf), "%s %s", (node->is_prefix() ? "PRE" : "POST"),
+  EmbeddedVector<char, 128> buf;
+  OS::SNPrintF(buf, "%s %s", (node->is_prefix() ? "PRE" : "POST"),
                Token::Name(node->op()));
-  PrintIndentedVisit(buf, node->expression());
+  PrintIndentedVisit(buf.start(), node->expression());
 }
 
 
index ba18ce85d0d6803f9ac0b1f82d02d3eb0f6f06f0..6478a9070a305098f1d94e443fbc8c933abb0531 100644 (file)
@@ -511,12 +511,12 @@ ExternalReferenceTable::ExternalReferenceTable() : refs_(64) {
   const char* debug_register_format = "Debug::register_address(%i)";
   size_t dr_format_length = strlen(debug_register_format);
   for (int i = 0; i < kNumJSCallerSaved; ++i) {
-    char* name = NewArray<char>(dr_format_length + 1);
-    OS::SNPrintF(name, dr_format_length, debug_register_format, i);
+    Vector<char> name = Vector<char>::New(dr_format_length + 1);
+    OS::SNPrintF(name, debug_register_format, i);
     Add(Debug_Address(Debug::k_register_address, i).address(),
         DEBUG_ADDRESS,
         Debug::k_register_address << kDebugIdShift | i,
-        name);
+        name.start());
   }
 
   // Stat counters
@@ -534,9 +534,10 @@ ExternalReferenceTable::ExternalReferenceTable() : refs_(64) {
   const char* top_address_format = "Top::get_address_from_id(%i)";
   size_t top_format_length = strlen(top_address_format);
   for (uint16_t i = 0; i < Top::k_top_address_count; ++i) {
-    char* name = NewArray<char>(top_format_length + 1);
-    OS::SNPrintF(name, top_format_length, top_address_format, i);
-    Add(Top::get_address_from_id((Top::AddressId)i), TOP_ADDRESS, i, name);
+    Vector<char> name = Vector<char>::New(top_format_length + 1);
+    const char* chars = name.start();
+    OS::SNPrintF(name, top_address_format, i);
+    Add(Top::get_address_from_id((Top::AddressId)i), TOP_ADDRESS, i, chars);
   }
 
   // Extensions
index 55dc402a44194004b00a01f79d395f65a2dab4aa..9ba6d870cb41fa754995033c754f85583588e0b7 100644 (file)
@@ -106,11 +106,7 @@ void StringStream::Add(const char* format, Vector<FmtElm> elms) {
       continue;
     }
     // Read this formatting directive into a temporary buffer
-    const int kTempSize = 24;
-    char temp_buffer[kTempSize];
-    // Wrap temp buffer in a vector to get bounds checking in debug
-    // mode
-    Vector<char> temp(temp_buffer, kTempSize);
+    EmbeddedVector<char, 24> temp;
     int format_length = 0;
     // Skip over the whole control character sequence until the
     // format element type
@@ -140,14 +136,9 @@ void StringStream::Add(const char* format, Vector<FmtElm> elms) {
     }
     case 'i': case 'd': case 'u': case 'x': case 'c': case 'p': {
       int value = current.data_.u_int_;
-      char formatted[kTempSize];
-#ifdef WIN32
-      // This is not my idea of a good time.
-      _snprintf(formatted, kTempSize, temp.start(), value);
-#else
-      snprintf(formatted, kTempSize, temp.start(), value);
-#endif
-      Add(formatted);
+      EmbeddedVector<char, 24> formatted;
+      OS::SNPrintF(formatted, temp.start(), value);
+      Add(formatted.start());
       break;
     }
     default:
index 061b3001c8906d438d14c382e57799e9935594f3..236bdedb960dccefe070a6b3f9370124db28afe3 100644 (file)
@@ -124,11 +124,11 @@ class PreallocatedMemoryThread: public Thread {
   // When the thread starts running it will allocate a fixed number of bytes
   // on the stack and publish the location of this memory for others to use.
   void Run() {
-    char local_buffer[16 * 1024];
+    EmbeddedVector<char, 16 * 1024> local_buffer;
 
     // Initialize the buffer with a known good value.
-    strncpy(local_buffer, "Trace data was not generated.\n",
-            sizeof(local_buffer));
+    OS::StrNCpy(local_buffer, "Trace data was not generated.\n",
+                local_buffer.length());
 
     // Publish the local buffer and signal its availability.
     data_ = &local_buffer[0];
@@ -142,8 +142,8 @@ class PreallocatedMemoryThread: public Thread {
 
     // Make sure we access the buffer after the wait to remove all possibility
     // of it being optimized away.
-    strncpy(local_buffer, "PreallocatedMemoryThread shutting down.\n",
-            sizeof(local_buffer));
+    OS::StrNCpy(local_buffer, "PreallocatedMemoryThread shutting down.\n",
+                local_buffer.length());
   }
 
   static char* data() {
index 8cfa2379de2af22de7770628bd517a396a02b9fb..9310301a15e8dae6cdd2ad0c7a8c66921374a6cc 100644 (file)
@@ -155,7 +155,7 @@ char* ReadCharsFromFile(const char* filename,
                         int* size,
                         int extra_space,
                         bool verbose) {
-  FILE* file = fopen(filename, "rb");
+  FILE* file = OS::FOpen(filename, "rb");
   if (file == NULL || fseek(file, 0, SEEK_END) != 0) {
     if (verbose) {
       OS::PrintError("Cannot read from file %s.\n", filename);
@@ -220,7 +220,7 @@ int WriteChars(const char* filename,
                const char* str,
                int size,
                bool verbose) {
-  FILE* f = fopen(filename, "wb");
+  FILE* f = OS::FOpen(filename, "wb");
   if (f == NULL) {
     if (verbose) {
       OS::PrintError("Cannot open file %s for reading.\n", filename);
@@ -234,8 +234,7 @@ int WriteChars(const char* filename,
 
 
 StringBuilder::StringBuilder(int size) {
-  buffer_ = NewArray<char>(size);
-  size_ = size;
+  buffer_ = Vector<char>::New(size);
   position_ = 0;
 }
 
@@ -246,7 +245,7 @@ void StringBuilder::AddString(const char* s) {
 
 
 void StringBuilder::AddSubstring(const char* s, int n) {
-  ASSERT(!is_finalized() && position_ + n < size_);
+  ASSERT(!is_finalized() && position_ + n < buffer_.length());
   ASSERT(static_cast<size_t>(n) <= strlen(s));
   memcpy(&buffer_[position_], s, n * kCharSize);
   position_ += n;
@@ -254,14 +253,13 @@ void StringBuilder::AddSubstring(const char* s, int n) {
 
 
 void StringBuilder::AddFormatted(const char* format, ...) {
-  ASSERT(!is_finalized() && position_ < size_);
+  ASSERT(!is_finalized() && position_ < buffer_.length());
   va_list args;
   va_start(args, format);
-  int remaining = size_ - position_;
-  int n = OS::VSNPrintF(&buffer_[position_], remaining, format, args);
+  int n = OS::VSNPrintF(buffer_ + position_, format, args);
   va_end(args);
-  if (n < 0 || n >= remaining) {
-    position_ = size_;
+  if (n < 0 || n >= (buffer_.length() - position_)) {
+    position_ = buffer_.length();
   } else {
     position_ += n;
   }
@@ -276,14 +274,14 @@ void StringBuilder::AddPadding(char c, int count) {
 
 
 char* StringBuilder::Finalize() {
-  ASSERT(!is_finalized() && position_ < size_);
+  ASSERT(!is_finalized() && position_ < buffer_.length());
   buffer_[position_] = '\0';
   // Make sure nobody managed to add a 0-character to the
   // buffer while building the string.
-  ASSERT(strlen(buffer_) == static_cast<size_t>(position_));
+  ASSERT(strlen(buffer_.start()) == static_cast<size_t>(position_));
   position_ = -1;
   ASSERT(is_finalized());
-  return buffer_;
+  return buffer_.start();
 }
 
 } }  // namespace v8::internal
index 1c07ba4c8f45d00f2877af214c1078672bd5eee4..38bbd16416fa804de97acb237c7cdedd2294839c 100644 (file)
@@ -279,6 +279,10 @@ class Vector {
     ASSERT(length == 0 || (length > 0 && data != NULL));
   }
 
+  static Vector<T> New(int length) {
+    return Vector<T>(NewArray<T>(length), length);
+  }
+
   // Returns the length of the vector.
   int length() const { return length_; }
 
@@ -310,6 +314,11 @@ class Vector {
     length_ = 0;
   }
 
+  inline Vector<T> operator+(int offset) {
+    ASSERT(offset < length_);
+    return Vector<T>(start_ + offset, length_ - offset);
+  }
+
   // Factory method for creating empty vectors.
   static Vector<T> empty() { return Vector<T>(NULL, 0); }
 
@@ -319,6 +328,15 @@ class Vector {
 };
 
 
+template <typename T, int size>
+class EmbeddedVector : public Vector<T> {
+ public:
+  EmbeddedVector() : Vector<T>(buffer_, size) { }
+ private:
+  T buffer_[size];
+};
+
+
 inline Vector<const char> CStrVector(const char* data) {
   return Vector<const char>(data, strlen(data));
 }
@@ -327,6 +345,11 @@ inline Vector<char> MutableCStrVector(char* data) {
   return Vector<char>(data, strlen(data));
 }
 
+inline Vector<char> MutableCStrVector(char* data, int max) {
+  int length = strlen(data);
+  return Vector<char>(data, (length < max) ? length : max);
+}
+
 template <typename T>
 inline Vector< Handle<Object> > HandleVector(v8::internal::Handle<T>* elms,
                                              int length) {
@@ -369,11 +392,11 @@ class StringBuilder {
   explicit StringBuilder(int size);
 
   StringBuilder(char* buffer, int size)
-      : buffer_(buffer), size_(size), position_(0) { }
+      : buffer_(buffersize), position_(0) { }
 
   ~StringBuilder() { if (!is_finalized()) Finalize(); }
 
-  int size() const { return size_; }
+  int size() const { return buffer_.length(); }
 
   // Get the current position in the builder.
   int position() const {
@@ -389,7 +412,7 @@ class StringBuilder {
   // instead.
   void AddCharacter(char c) {
     ASSERT(c != '\0');
-    ASSERT(!is_finalized() && position_ < size_);
+    ASSERT(!is_finalized() && position_ < buffer_.length());
     buffer_[position_++] = c;
   }
 
@@ -412,8 +435,7 @@ class StringBuilder {
   char* Finalize();
 
  private:
-  char* buffer_;
-  int size_;
+  Vector<char> buffer_;
   int position_;
 
   bool is_finalized() const { return position_ < 0; }
index 6591f17b4898e48e294180471fcc2a77f933a215..e9c8f0d67b4e5f882dd63a4073f643dd4f5ddde0 100644 (file)
@@ -44,9 +44,9 @@ CcTest::CcTest(TestFunction* callback, const char* file,
     basename = strrchr(const_cast<char *>(file), '\\');
   }
   if (!basename) {
-    basename = strdup(file);
+    basename = v8::internal::OS::StrDup(file);
   } else {
-    basename = strdup(basename + 1);
+    basename = v8::internal::OS::StrDup(basename + 1);
   }
   // Drop the extension, if there is one.
   char *extension = strrchr(basename, '.');
@@ -77,7 +77,7 @@ int main(int argc, char* argv[]) {
       print_run_count = false;
 
     } else {
-      char* arg_copy = strdup(arg);
+      char* arg_copy = v8::internal::OS::StrDup(arg);
       char* testname = strchr(arg_copy, '/');
       if (testname) {
         // Split the string in two by nulling the slash and then run
index dca36e25207173f9448c8ad3aed717a84b0e3617..38478cfac1abe1987191d0e5763d93eed1245b79 100644 (file)
@@ -77,10 +77,10 @@ static Handle<JSFunction> Compile(const char* source) {
 
 static double Inc(int x) {
   const char* source = "result = %d + 1;";
-  char buffer[512];
-  OS::SNPrintF(buffer, sizeof(buffer), source, x);
+  EmbeddedVector<char, 512> buffer;
+  OS::SNPrintF(buffer, source, x);
 
-  Handle<JSFunction> fun = Compile(buffer);
+  Handle<JSFunction> fun = Compile(buffer.start());
   if (fun.is_null()) return -1;
 
   bool has_pending_exception;
index 89fcb366e0510faee36fab5762efea6fa0555a42..277a5451b306fb7b2927dfbbacc2eb5cfbc0043b 100644 (file)
@@ -35,6 +35,8 @@
 #include "stub-cache.h"
 #include "cctest.h"
 
+
+using ::v8::internal::EmbeddedVector;
 using ::v8::internal::Object;
 using ::v8::internal::OS;
 using ::v8::internal::Handle;
@@ -203,33 +205,34 @@ static int SetBreakPoint(v8::Handle<v8::Function> fun, int position) {
 // associated break point number.
 static int SetBreakPointFromJS(const char* function_name,
                                int line, int position) {
-  char buffer[SMALL_STRING_BUFFER_SIZE];
-  OS::SNPrintF(buffer, SMALL_STRING_BUFFER_SIZE,
+  EmbeddedVector<char, SMALL_STRING_BUFFER_SIZE> buffer;
+  OS::SNPrintF(buffer,
                "debug.Debug.setBreakPoint(%s,%d,%d)",
                function_name, line, position);
   buffer[SMALL_STRING_BUFFER_SIZE - 1] = '\0';
-  return v8::Script::Compile(v8::String::New(buffer))->Run()->Int32Value();
+  v8::Handle<v8::String> str = v8::String::New(buffer.start());
+  return v8::Script::Compile(str)->Run()->Int32Value();
 }
 
 
 // Set a break point in a script using the global Debug object.
 static int SetScriptBreakPointFromJS(const char* script_data,
                                      int line, int column) {
-  char buffer[SMALL_STRING_BUFFER_SIZE];
+  EmbeddedVector<char, SMALL_STRING_BUFFER_SIZE> buffer;
   if (column >= 0) {
     // Column specified set script break point on precise location.
-    OS::SNPrintF(buffer, SMALL_STRING_BUFFER_SIZE,
+    OS::SNPrintF(buffer,
                  "debug.Debug.setScriptBreakPoint(\"%s\",%d,%d)",
                  script_data, line, column);
   } else {
     // Column not specified set script break point on line.
-    OS::SNPrintF(buffer, SMALL_STRING_BUFFER_SIZE,
+    OS::SNPrintF(buffer,
                  "debug.Debug.setScriptBreakPoint(\"%s\",%d)",
                  script_data, line);
   }
   buffer[SMALL_STRING_BUFFER_SIZE - 1] = '\0';
-
-  return v8::Script::Compile(v8::String::New(buffer))->Run()->Int32Value();
+  v8::Handle<v8::String> str = v8::String::New(buffer.start());
+  return v8::Script::Compile(str)->Run()->Int32Value();
 }
 
 
@@ -242,54 +245,54 @@ static void ClearBreakPoint(int break_point) {
 
 // Clear a break point using the global Debug object.
 static void ClearBreakPointFromJS(int break_point_number) {
-  char buffer[SMALL_STRING_BUFFER_SIZE];
-  OS::SNPrintF(buffer, SMALL_STRING_BUFFER_SIZE,
+  EmbeddedVector<char, SMALL_STRING_BUFFER_SIZE> buffer;
+  OS::SNPrintF(buffer,
                "debug.Debug.clearBreakPoint(%d)",
                break_point_number);
   buffer[SMALL_STRING_BUFFER_SIZE - 1] = '\0';
-  v8::Script::Compile(v8::String::New(buffer))->Run();
+  v8::Script::Compile(v8::String::New(buffer.start()))->Run();
 }
 
 
 static void EnableScriptBreakPointFromJS(int break_point_number) {
-  char buffer[SMALL_STRING_BUFFER_SIZE];
-  OS::SNPrintF(buffer, SMALL_STRING_BUFFER_SIZE,
+  EmbeddedVector<char, SMALL_STRING_BUFFER_SIZE> buffer;
+  OS::SNPrintF(buffer,
                "debug.Debug.enableScriptBreakPoint(%d)",
                break_point_number);
   buffer[SMALL_STRING_BUFFER_SIZE - 1] = '\0';
-  v8::Script::Compile(v8::String::New(buffer))->Run();
+  v8::Script::Compile(v8::String::New(buffer.start()))->Run();
 }
 
 
 static void DisableScriptBreakPointFromJS(int break_point_number) {
-  char buffer[SMALL_STRING_BUFFER_SIZE];
-  OS::SNPrintF(buffer, SMALL_STRING_BUFFER_SIZE,
+  EmbeddedVector<char, SMALL_STRING_BUFFER_SIZE> buffer;
+  OS::SNPrintF(buffer,
                "debug.Debug.disableScriptBreakPoint(%d)",
                break_point_number);
   buffer[SMALL_STRING_BUFFER_SIZE - 1] = '\0';
-  v8::Script::Compile(v8::String::New(buffer))->Run();
+  v8::Script::Compile(v8::String::New(buffer.start()))->Run();
 }
 
 
 static void ChangeScriptBreakPointConditionFromJS(int break_point_number,
                                                   const char* condition) {
-  char buffer[SMALL_STRING_BUFFER_SIZE];
-  OS::SNPrintF(buffer, SMALL_STRING_BUFFER_SIZE,
+  EmbeddedVector<char, SMALL_STRING_BUFFER_SIZE> buffer;
+  OS::SNPrintF(buffer,
                "debug.Debug.changeScriptBreakPointCondition(%d, \"%s\")",
                break_point_number, condition);
   buffer[SMALL_STRING_BUFFER_SIZE - 1] = '\0';
-  v8::Script::Compile(v8::String::New(buffer))->Run();
+  v8::Script::Compile(v8::String::New(buffer.start()))->Run();
 }
 
 
 static void ChangeScriptBreakPointIgnoreCountFromJS(int break_point_number,
                                                     int ignoreCount) {
-  char buffer[SMALL_STRING_BUFFER_SIZE];
-  OS::SNPrintF(buffer, SMALL_STRING_BUFFER_SIZE,
+  EmbeddedVector<char, SMALL_STRING_BUFFER_SIZE> buffer;
+  OS::SNPrintF(buffer,
                "debug.Debug.changeScriptBreakPointIgnoreCount(%d, %d)",
                break_point_number, ignoreCount);
   buffer[SMALL_STRING_BUFFER_SIZE - 1] = '\0';
-  v8::Script::Compile(v8::String::New(buffer))->Run();
+  v8::Script::Compile(v8::String::New(buffer.start()))->Run();
 }
 
 
index 8f06f0f4a5f0779a081aafbff0553dc97b963e43..187cba944b24cc6f8f93f8270a2c3455b64c36b0 100644 (file)
@@ -162,17 +162,17 @@ TEST(SNPrintF) {
   int length = strlen(s);
   for (int i = 1; i < length * 2; i++) {
     static const char kMarker = static_cast<char>(42);
-    char* buffer = NewArray<char>(i + 1);
+    Vector<char> buffer = Vector<char>::New(i + 1);
     buffer[i] = kMarker;
-    int n = OS::SNPrintF(buffer, i, "%s", s);
+    int n = OS::SNPrintF(Vector<char>(buffer.start(), i), "%s", s);
     CHECK(n <= i);
     CHECK(n == length || n == -1);
-    CHECK_EQ(0, strncmp(buffer, s, i - 1));
+    CHECK_EQ(0, strncmp(buffer.start(), s, i - 1));
     CHECK_EQ(kMarker, buffer[i]);
     if (i <= length) {
-      CHECK_EQ(i - 1, strlen(buffer));
+      CHECK_EQ(i - 1, strlen(buffer.start()));
     } else {
-      CHECK_EQ(length, strlen(buffer));
+      CHECK_EQ(length, strlen(buffer.start()));
     }
   }
 }