Bug 488808: crash due to JSString INIT macros stomping deflated flag, r=brendan

This commit is contained in:
David Mandelin 2009-04-17 19:30:26 -07:00
Родитель a53703f832
Коммит 60c7bc2aa1
3 изменённых файлов: 29 добавлений и 4 удалений

Просмотреть файл

@ -5449,7 +5449,7 @@ JS_GetStringChars(JSString *str)
if (s) {
memcpy(s, JSSTRDEP_CHARS(str), n * sizeof *s);
s[n] = 0;
JSFLATSTR_INIT(str, s, n);
JSFLATSTR_REINIT(str, s, n);
} else {
s = JSSTRDEP_CHARS(str);
}

Просмотреть файл

@ -99,7 +99,7 @@ js_MinimizeDependentStrings(JSString *str, int level, JSString **basep)
JSPREFIX_SET_BASE(str, base);
} else if (start <= JSSTRDEP_START_MASK) {
length = JSSTRDEP_LENGTH(str);
JSSTRDEP_INIT(str, base, start, length);
JSSTRDEP_REINIT(str, base, start, length);
}
}
*basep = base;
@ -182,7 +182,7 @@ js_ConcatStrings(JSContext *cx, JSString *left, JSString *right)
/* Morph left into a dependent prefix if we realloc'd its buffer. */
if (ldep) {
JSPREFIX_INIT(ldep, str, ln);
JSPREFIX_REINIT(ldep, str, ln);
#ifdef DEBUG
{
JSRuntime *rt = cx->runtime;
@ -214,7 +214,7 @@ js_UndependString(JSContext *cx, JSString *str)
js_strncpy(s, JSSTRDEP_CHARS(str), n);
s[n] = 0;
JSFLATSTR_INIT(str, s, n);
JSFLATSTR_REINIT(str, s, n);
#ifdef DEBUG
{

Просмотреть файл

@ -168,6 +168,17 @@ JS_STATIC_ASSERT(sizeof(size_t) == sizeof(jsword));
#define JSFLATSTR_CHARS(str) \
(JS_ASSERT(JSSTRING_IS_FLAT(str)), (str)->u.chars)
/*
* Special flat string initializer that preserves the JSSTR_DEFLATED flag.
* Use this macro when reinitializing an existing string (which may be
* hashed to its deflated bytes. Newborn strings must use JSFLATSTR_INIT.
*/
#define JSFLATSTR_REINIT(str, chars_, length_) \
((void)(JS_ASSERT(((length_) & ~JSSTRING_LENGTH_MASK) == 0), \
(str)->length = ((str)->length & JSSTRFLAG_DEFLATED) | \
(length_ & ~JSSTRFLAG_DEFLATED), \
(str)->u.chars = (chars_)))
/*
* Macros to manipulate atomized and mutable flags of flat strings. It is safe
* to use these without extra locking due to the following properties:
@ -233,10 +244,24 @@ JS_STATIC_ASSERT(sizeof(size_t) == sizeof(jsword));
| (len), \
(str)->u.base = (bstr))
/* See JSFLATSTR_INIT. */
#define JSSTRDEP_REINIT(str,bstr,off,len) \
((str)->length = JSSTRFLAG_DEPENDENT \
| ((str->length) & JSSTRFLAG_DEFLATED) \
| ((off) << JSSTRDEP_START_SHIFT) \
| (len), \
(str)->u.base = (bstr))
#define JSPREFIX_INIT(str,bstr,len) \
((str)->length = JSSTRFLAG_DEPENDENT | JSSTRFLAG_PREFIX | (len), \
(str)->u.base = (bstr))
/* See JSFLATSTR_INIT. */
#define JSPREFIX_REINIT(str,bstr,len) \
((str)->length = JSSTRFLAG_DEPENDENT | JSSTRFLAG_PREFIX | \
((str->length) & JSSTRFLAG_DEFLATED) | (len), \
(str)->u.base = (bstr))
#define JSSTRDEP_BASE(str) ((str)->u.base)
#define JSPREFIX_BASE(str) JSSTRDEP_BASE(str)
#define JSPREFIX_SET_BASE(str,bstr) ((str)->u.base = (bstr))