1 : /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
2 : *
3 : * This Source Code Form is subject to the terms of the Mozilla Public
4 : * License, v. 2.0. If a copy of the MPL was not distributed with this file,
5 : * You can obtain one at http://mozilla.org/MPL/2.0/. */
6 :
7 : #include "vm/StringBuffer.h"
8 :
9 : #include "jsobjinlines.h"
10 :
11 : #include "vm/String-inl.h"
12 : #include "vm/StringBuffer-inl.h"
13 :
14 : using namespace js;
15 :
16 : jschar *
17 271334 : StringBuffer::extractWellSized()
18 : {
19 271334 : size_t capacity = cb.capacity();
20 271334 : size_t length = cb.length();
21 :
22 271334 : jschar *buf = cb.extractRawBuffer();
23 271334 : if (!buf)
24 0 : return NULL;
25 :
26 : /* For medium/big buffers, avoid wasting more than 1/4 of the memory. */
27 271334 : JS_ASSERT(capacity >= length);
28 271334 : if (length > CharBuffer::sMaxInlineStorage && capacity - length > length / 4) {
29 51532 : size_t bytes = sizeof(jschar) * (length + 1);
30 51532 : JSContext *cx = context();
31 51532 : jschar *tmp = (jschar *)cx->realloc_(buf, bytes);
32 51532 : if (!tmp) {
33 0 : cx->free_(buf);
34 0 : return NULL;
35 : }
36 51532 : buf = tmp;
37 : }
38 :
39 271334 : return buf;
40 : }
41 :
42 : JSFixedString *
43 466268 : StringBuffer::finishString()
44 : {
45 466268 : JSContext *cx = context();
46 466268 : if (cb.empty())
47 80647 : return cx->runtime->atomState.emptyAtom;
48 :
49 385621 : size_t length = cb.length();
50 385621 : if (!checkLength(length))
51 0 : return NULL;
52 :
53 : JS_STATIC_ASSERT(JSShortString::MAX_SHORT_LENGTH < CharBuffer::InlineLength);
54 385621 : if (JSShortString::lengthFits(length))
55 114287 : return NewShortString(cx, cb.begin(), length);
56 :
57 271334 : if (!cb.append('\0'))
58 0 : return NULL;
59 :
60 271334 : jschar *buf = extractWellSized();
61 271334 : if (!buf)
62 0 : return NULL;
63 :
64 271334 : JSFixedString *str = js_NewString(cx, buf, length);
65 271334 : if (!str)
66 0 : cx->free_(buf);
67 271334 : return str;
68 : }
69 :
70 : JSAtom *
71 3916 : StringBuffer::finishAtom()
72 : {
73 3916 : JSContext *cx = context();
74 :
75 3916 : size_t length = cb.length();
76 3916 : if (length == 0)
77 0 : return cx->runtime->atomState.emptyAtom;
78 :
79 3916 : JSAtom *atom = js_AtomizeChars(cx, cb.begin(), length);
80 3916 : cb.clear();
81 3916 : return atom;
82 : }
83 :
84 : bool
85 692695 : js::ValueToStringBufferSlow(JSContext *cx, const Value &arg, StringBuffer &sb)
86 : {
87 692695 : Value v = arg;
88 692695 : if (!ToPrimitive(cx, JSTYPE_STRING, &v))
89 9 : return false;
90 :
91 692686 : if (v.isString())
92 1213 : return sb.append(v.toString());
93 691473 : if (v.isNumber())
94 643562 : return NumberValueToStringBuffer(cx, v, sb);
95 47911 : if (v.isBoolean())
96 47875 : return BooleanToStringBuffer(cx, v.toBoolean(), sb);
97 36 : if (v.isNull())
98 0 : return sb.append(cx->runtime->atomState.nullAtom);
99 36 : JS_ASSERT(v.isUndefined());
100 36 : return sb.append(cx->runtime->atomState.typeAtoms[JSTYPE_VOID]);
101 : }
|