From 4e8cddddcbb7af0d7dcb39dabce6b48cef8c9957 Mon Sep 17 00:00:00 2001 From: isaacs Date: Thu, 2 May 2013 10:49:20 -0700 Subject: [PATCH] src: use StringBytes for DecodeWrite/DecodeBytes/Encode Bonus: this makes node::Encode actually work properly with base64, ucs2, hex, etc. --- src/node.cc | 97 ++++------------------------------------------------- 1 file changed, 7 insertions(+), 90 deletions(-) diff --git a/src/node.cc b/src/node.cc index 97e64a73b09..9b27bfd5b0b 100644 --- a/src/node.cc +++ b/src/node.cc @@ -22,6 +22,7 @@ #include "node.h" #include "req_wrap.h" #include "handle_wrap.h" +#include "string_bytes.h" #include "ares.h" #include "uv.h" @@ -1137,30 +1138,9 @@ enum encoding ParseEncoding(Handle encoding_v, enum encoding _default) { } Local Encode(const void *buf, size_t len, enum encoding encoding) { - HandleScope scope; - - if (encoding == BUFFER) { - return scope.Close( - Buffer::New(static_cast(buf), len)->handle_); - } - - if (!len) return scope.Close(String::Empty()); - - if (encoding == BINARY) { - const unsigned char *cbuf = static_cast(buf); - uint16_t * twobytebuf = new uint16_t[len]; - for (size_t i = 0; i < len; i++) { - // XXX is the following line platform independent? - twobytebuf[i] = cbuf[i]; - } - Local chunk = String::New(twobytebuf, len); - delete [] twobytebuf; // TODO use ExternalTwoByteString? - return scope.Close(chunk); - } - - // utf8 or ascii encoding - Local chunk = String::New((const char*)buf, len); - return scope.Close(chunk); + return StringBytes::Encode(static_cast(buf), + len, + encoding); } // Returns -1 if the handle was not valid for decoding @@ -1174,17 +1154,7 @@ ssize_t DecodeBytes(v8::Handle val, enum encoding encoding) { return -1; } - if ((encoding == BUFFER || encoding == BINARY) && Buffer::HasInstance(val)) { - return Buffer::Length(val->ToObject()); - } - - Local str = val->ToString(); - - if (encoding == UTF8) return str->Utf8Length(); - else if (encoding == UCS2) return str->Length() * 2; - else if (encoding == HEX) return str->Length() / 2; - - return str->Length(); + return StringBytes::Size(val, encoding); } #ifndef MIN @@ -1198,66 +1168,13 @@ ssize_t DecodeWrite(char *buf, enum encoding encoding) { HandleScope scope; - // XXX - // A lot of improvement can be made here. See: - // http://code.google.com/p/v8/issues/detail?id=270 - // http://groups.google.com/group/v8-dev/browse_thread/thread/dba28a81d9215291/ece2b50a3b4022c - // http://groups.google.com/group/v8-users/browse_thread/thread/1f83b0ba1f0a611 - if (val->IsArray()) { - fprintf(stderr, "'raw' encoding (array of integers) has been removed. " - "Use 'binary'.\n"); + fprintf(stderr, "'raw' encoding (array of integers) has been removed.\n"); assert(0); return -1; } - bool is_buffer = Buffer::HasInstance(val); - - if (is_buffer && (encoding == BINARY || encoding == BUFFER)) { - // fast path, copy buffer data - const char* data = Buffer::Data(val.As()); - size_t size = Buffer::Length(val.As()); - size_t len = size < buflen ? size : buflen; - memcpy(buf, data, len); - return len; - } - - Local str; - - if (is_buffer) { // slow path, convert to binary string - Local arg = String::New("binary"); - str = MakeCallback(val.As(), "toString", 1, &arg)->ToString(); - } - else { - str = val->ToString(); - } - - if (encoding == UTF8) { - str->WriteUtf8(buf, buflen, NULL, String::HINT_MANY_WRITES_EXPECTED); - return buflen; - } - - if (encoding == ASCII) { - str->WriteAscii(buf, 0, buflen, String::HINT_MANY_WRITES_EXPECTED); - return buflen; - } - - // THIS IS AWFUL!!! FIXME - - assert(encoding == BINARY); - - uint16_t * twobytebuf = new uint16_t[buflen]; - - str->Write(twobytebuf, 0, buflen, String::HINT_MANY_WRITES_EXPECTED); - - for (size_t i = 0; i < buflen; i++) { - unsigned char *b = reinterpret_cast(&twobytebuf[i]); - buf[i] = b[0]; - } - - delete [] twobytebuf; - - return buflen; + return StringBytes::Write(buf, buflen, val, encoding, NULL); } void DisplayExceptionLine (TryCatch &try_catch) {