зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1658593 - Bugfixes in ParserAtoms implementation. r=tcampbell
Differential Revision: https://phabricator.services.mozilla.com/D86734
This commit is contained in:
Родитель
f7e148af42
Коммит
b430e79e18
|
@ -101,26 +101,28 @@ bool ParserAtomEntry::equalsJSAtom(JSAtom* other) const {
|
|||
: EqualChars(latin1Chars(), other->twoByteChars(nogc), length_);
|
||||
}
|
||||
|
||||
UniqueChars ParserAtomToPrintableString(JSContext* cx, const ParserAtom* atom) {
|
||||
template <typename CharT>
|
||||
UniqueChars ToPrintableStringImpl(JSContext* cx, mozilla::Range<CharT> str) {
|
||||
Sprinter sprinter(cx);
|
||||
if (!sprinter.init()) {
|
||||
return nullptr;
|
||||
}
|
||||
size_t length = atom->length();
|
||||
if (atom->hasLatin1Chars()) {
|
||||
if (!QuoteString<QuoteTarget::String>(
|
||||
&sprinter, mozilla::Range(atom->latin1Chars(), length))) {
|
||||
if (!QuoteString<QuoteTarget::String>(&sprinter, str)) {
|
||||
return nullptr;
|
||||
}
|
||||
} else {
|
||||
if (!QuoteString<QuoteTarget::String>(
|
||||
&sprinter, mozilla::Range(atom->twoByteChars(), length))) {
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
return sprinter.release();
|
||||
}
|
||||
|
||||
UniqueChars ParserAtomToPrintableString(JSContext* cx, const ParserAtom* atom) {
|
||||
size_t length = atom->length();
|
||||
|
||||
return atom->hasLatin1Chars()
|
||||
? ToPrintableStringImpl(
|
||||
cx, mozilla::Range(atom->latin1Chars(), length))
|
||||
: ToPrintableStringImpl(
|
||||
cx, mozilla::Range(atom->twoByteChars(), length));
|
||||
}
|
||||
|
||||
bool ParserAtomEntry::isIndex(uint32_t* indexp) const {
|
||||
size_t len = length();
|
||||
if (len == 0 || len > UINT32_CHAR_BUFFER_LENGTH) {
|
||||
|
@ -155,6 +157,16 @@ bool ParserAtomEntry::toNumber(JSContext* cx, double* result) const {
|
|||
: CharsToNumber(cx, twoByteChars(), length(), result);
|
||||
}
|
||||
|
||||
#if defined(DEBUG) || defined(JS_JITSPEW)
|
||||
void ParserAtomEntry::dumpCharsNoQuote(js::GenericPrinter& out) const {
|
||||
if (hasLatin1Chars()) {
|
||||
JSString::dumpCharsNoQuote<Latin1Char>(latin1Chars(), length(), out);
|
||||
} else {
|
||||
JSString::dumpCharsNoQuote<char16_t>(twoByteChars(), length(), out);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
ParserAtomsTable::ParserAtomsTable(JSContext* cx)
|
||||
: entrySet_(cx), wellKnownTable_(*cx->runtime()->commonParserNames) {}
|
||||
|
||||
|
@ -425,21 +437,37 @@ bool WellKnownParserAtoms::initSingle(JSContext* cx, const ParserName** name,
|
|||
MOZ_ASSERT(FindSmallestEncoding(UTF8Chars(str, len)) ==
|
||||
JS::SmallestEncoding::ASCII);
|
||||
|
||||
InflatedChar16Sequence<Latin1Char> seq(
|
||||
reinterpret_cast<const Latin1Char*>(str), len);
|
||||
SpecificParserAtomLookup<Latin1Char> lookup(seq);
|
||||
HashNumber hash = lookup.hash();
|
||||
|
||||
UniquePtr<ParserAtomEntry> entry = nullptr;
|
||||
|
||||
// Check for inline allocation.
|
||||
if (len <= ParserAtomEntry::MaxInline<Latin1Char>()) {
|
||||
auto maybeEntry =
|
||||
ParserAtomEntry::allocateInline<Latin1Char>(cx, seq, len, hash);
|
||||
if (maybeEntry.isErr()) {
|
||||
return false;
|
||||
}
|
||||
entry = maybeEntry.unwrap();
|
||||
|
||||
// Do heap-allocation of contents.
|
||||
} else {
|
||||
UniqueLatin1Chars copy(cx->pod_malloc<Latin1Char>(len));
|
||||
if (!copy) {
|
||||
return false;
|
||||
}
|
||||
mozilla::PodCopy(copy.get(), reinterpret_cast<const Latin1Char*>(str), len);
|
||||
|
||||
InflatedChar16Sequence<Latin1Char> seq(copy.get(), len);
|
||||
SpecificParserAtomLookup<Latin1Char> lookup(seq);
|
||||
|
||||
auto maybeEntry =
|
||||
ParserAtomEntry::allocate(cx, std::move(copy), len, lookup.hash());
|
||||
auto maybeEntry = ParserAtomEntry::allocate(cx, std::move(copy), len, hash);
|
||||
if (maybeEntry.isErr()) {
|
||||
return false;
|
||||
}
|
||||
UniquePtr<ParserAtomEntry> entry = maybeEntry.unwrap();
|
||||
entry = maybeEntry.unwrap();
|
||||
}
|
||||
|
||||
// Save name for returning after moving entry into set.
|
||||
const ParserName* nm = entry.get()->asName();
|
||||
if (!entrySet_.putNew(lookup, std::move(entry))) {
|
||||
return false;
|
||||
|
|
|
@ -43,6 +43,7 @@ mozilla::GenericErrorResult<OOM&> RaiseParserAtomsOOMError(JSContext* cx);
|
|||
*/
|
||||
class alignas(alignof(void*)) ParserAtomEntry {
|
||||
friend class ParserAtomsTable;
|
||||
friend class WellKnownParserAtoms;
|
||||
|
||||
template <typename CharT>
|
||||
static constexpr uint32_t MaxInline() {
|
||||
|
@ -279,6 +280,10 @@ class alignas(alignof(void*)) ParserAtomEntry {
|
|||
|
||||
// Convert this entry to a number.
|
||||
bool toNumber(JSContext* cx, double* result) const;
|
||||
|
||||
#if defined(DEBUG) || defined(JS_JITSPEW)
|
||||
void dumpCharsNoQuote(js::GenericPrinter& out) const;
|
||||
#endif
|
||||
};
|
||||
|
||||
class ParserAtom : public ParserAtomEntry {
|
||||
|
@ -483,10 +488,6 @@ inline bool ParserAtomEntry::equalsSeq(
|
|||
return false;
|
||||
}
|
||||
}
|
||||
if (seq.hasMore()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
} else {
|
||||
const Latin1Char* chars = latin1Chars();
|
||||
for (uint32_t i = 0; i < length_; i++) {
|
||||
|
@ -494,11 +495,8 @@ inline bool ParserAtomEntry::equalsSeq(
|
|||
return false;
|
||||
}
|
||||
}
|
||||
if (seq.hasMore()) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
return !seq.hasMore();
|
||||
}
|
||||
|
||||
} /* namespace frontend */
|
||||
|
|
Загрузка…
Ссылка в новой задаче