Introduce a new non-heap-allocated type for holding nsStringBuffer* in the HTML parser.

master
Fedor 2019-09-05 20:03:31 +03:00
parent 9c0a72c8e7
commit da7905c861
34 changed files with 719 additions and 358 deletions

View File

@ -39,6 +39,7 @@ EXPORTS += [
'nsHtml5SpeculativeLoad.h',
'nsHtml5StreamListener.h',
'nsHtml5StreamParser.h',
'nsHtml5String.h',
'nsHtml5StringParser.h',
'nsHtml5SVGLoadDispatcher.h',
'nsHtml5TreeOperation.h',
@ -78,6 +79,7 @@ UNIFIED_SOURCES += [
'nsHtml5StateSnapshot.cpp',
'nsHtml5StreamListener.cpp',
'nsHtml5StreamParser.cpp',
'nsHtml5String.cpp',
'nsHtml5StringParser.cpp',
'nsHtml5SVGLoadDispatcher.cpp',
'nsHtml5Tokenizer.cpp',

View File

@ -51,10 +51,11 @@ class nsHtml5ArrayCopy {
memcpy(target, source, size_t(length) * sizeof(int32_t));
}
static inline void
arraycopy(nsString** source, nsString** target, int32_t length)
static inline void arraycopy(nsHtml5String* source,
nsHtml5String* target,
int32_t length)
{
memcpy(target, source, size_t(length) * sizeof(nsString*));
memcpy(target, source, size_t(length) * sizeof(nsHtml5String));
}
static inline void

View File

@ -29,7 +29,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"

View File

@ -30,7 +30,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"

View File

@ -29,7 +29,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"

View File

@ -30,7 +30,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"

View File

@ -91,7 +91,7 @@ nsHtml5Highlighter::Start(const nsAutoString& aTitle)
if (length > INT32_MAX) {
length = INT32_MAX;
}
AppendCharacters(aTitle.get(), 0, (int32_t)length);
AppendCharacters(aTitle.BeginReading(), 0, (int32_t)length);
Pop(); // title
Push(nsGkAtoms::link, nsHtml5ViewSourceUtils::NewLinkAttributes());
@ -105,7 +105,7 @@ nsHtml5Highlighter::Start(const nsAutoString& aTitle)
Push(nsGkAtoms::body, nsHtml5ViewSourceUtils::NewBodyAttributes());
nsHtml5HtmlAttributes* preAttrs = new nsHtml5HtmlAttributes(0);
nsString* preId = new nsString(NS_LITERAL_STRING("line1"));
nsHtml5String preId = nsHtml5Portability::newStringFromLiteral("line1");
preAttrs->addAttribute(nsHtml5AttributeName::ATTR_ID, preId, -1);
Push(nsGkAtoms::pre, preAttrs);
@ -618,7 +618,7 @@ nsHtml5Highlighter::FlushOps()
void
nsHtml5Highlighter::MaybeLinkifyAttributeValue(nsHtml5AttributeName* aName,
nsString* aValue)
nsHtml5String aValue)
{
if (!(nsHtml5AttributeName::ATTR_HREF == aName ||
nsHtml5AttributeName::ATTR_SRC == aName ||
@ -630,7 +630,7 @@ nsHtml5Highlighter::MaybeLinkifyAttributeValue(nsHtml5AttributeName* aName,
nsHtml5AttributeName::ATTR_DEFINITIONURL == aName)) {
return;
}
AddViewSourceHref(*aValue);
AddViewSourceHref(aValue);
}
void
@ -717,10 +717,10 @@ nsHtml5Highlighter::AddClass(const char16_t* aClass)
}
void
nsHtml5Highlighter::AddViewSourceHref(const nsString& aValue)
nsHtml5Highlighter::AddViewSourceHref(nsHtml5String aValue)
{
char16_t* bufferCopy = new char16_t[aValue.Length() + 1];
memcpy(bufferCopy, aValue.get(), aValue.Length() * sizeof(char16_t));
aValue.CopyToBuffer(bufferCopy);
bufferCopy[aValue.Length()] = 0;
mOpQueue.AppendElement()->Init(eTreeOpAddViewSourceHref,
@ -730,14 +730,14 @@ nsHtml5Highlighter::AddViewSourceHref(const nsString& aValue)
}
void
nsHtml5Highlighter::AddBase(const nsString& aValue)
nsHtml5Highlighter::AddBase(nsHtml5String aValue)
{
if(mSeenBase) {
return;
}
mSeenBase = true;
char16_t* bufferCopy = new char16_t[aValue.Length() + 1];
memcpy(bufferCopy, aValue.get(), aValue.Length() * sizeof(char16_t));
aValue.CopyToBuffer(bufferCopy);
bufferCopy[aValue.Length()] = 0;
mOpQueue.AppendElement()->Init(eTreeOpAddViewSourceBase,

View File

@ -78,7 +78,7 @@ class nsHtml5Highlighter
* @param aValue the value of the attribute
*/
void MaybeLinkifyAttributeValue(nsHtml5AttributeName* aName,
nsString* aValue);
nsHtml5String aValue);
/**
* Inform the highlighter that the tokenizer successfully completed a
@ -147,7 +147,7 @@ class nsHtml5Highlighter
*
* @param aValue the base URL to add
*/
void AddBase(const nsString& aValue);
void AddBase(nsHtml5String aValue);
private:
@ -272,7 +272,7 @@ class nsHtml5Highlighter
*
* @param aValue the (potentially relative) URL to link to
*/
void AddViewSourceHref(const nsString& aValue);
void AddViewSourceHref(nsHtml5String aValue);
/**
* The state we are transitioning away from.

View File

@ -30,7 +30,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"
@ -58,11 +58,11 @@
nsHtml5HtmlAttributes* nsHtml5HtmlAttributes::EMPTY_ATTRIBUTES = nullptr;
nsHtml5HtmlAttributes::nsHtml5HtmlAttributes(int32_t mode)
: mode(mode),
length(0),
names(jArray<nsHtml5AttributeName*,int32_t>::newJArray(8)),
values(jArray<nsString*,int32_t>::newJArray(8)),
lines(jArray<int32_t,int32_t>::newJArray(8))
: mode(mode)
, length(0)
, names(jArray<nsHtml5AttributeName*, int32_t>::newJArray(8))
, values(jArray<nsHtml5String, int32_t>::newJArray(8))
, lines(jArray<int32_t, int32_t>::newJArray(8))
{
MOZ_COUNT_CTOR(nsHtml5HtmlAttributes);
}
@ -85,7 +85,7 @@ nsHtml5HtmlAttributes::getIndex(nsHtml5AttributeName* name)
return -1;
}
nsString*
nsHtml5String
nsHtml5HtmlAttributes::getValue(nsHtml5AttributeName* name)
{
int32_t index = getIndex(name);
@ -123,7 +123,7 @@ nsHtml5HtmlAttributes::getPrefixNoBoundsCheck(int32_t index)
return names[index]->getPrefix(mode);
}
nsString*
nsHtml5String
nsHtml5HtmlAttributes::getValueNoBoundsCheck(int32_t index)
{
MOZ_ASSERT(index < length && index >= 0, "Index out of bounds");
@ -145,14 +145,17 @@ nsHtml5HtmlAttributes::getLineNoBoundsCheck(int32_t index)
}
void
nsHtml5HtmlAttributes::addAttribute(nsHtml5AttributeName* name, nsString* value, int32_t line)
nsHtml5HtmlAttributes::addAttribute(nsHtml5AttributeName* name,
nsHtml5String value,
int32_t line)
{
if (names.length == length) {
int32_t newLen = length << 1;
jArray<nsHtml5AttributeName*,int32_t> newNames = jArray<nsHtml5AttributeName*,int32_t>::newJArray(newLen);
nsHtml5ArrayCopy::arraycopy(names, newNames, names.length);
names = newNames;
jArray<nsString*,int32_t> newValues = jArray<nsString*,int32_t>::newJArray(newLen);
jArray<nsHtml5String, int32_t> newValues =
jArray<nsHtml5String, int32_t>::newJArray(newLen);
nsHtml5ArrayCopy::arraycopy(values, newValues, values.length);
values = newValues;
jArray<int32_t,int32_t> newLines = jArray<int32_t,int32_t>::newJArray(newLen);
@ -171,7 +174,7 @@ nsHtml5HtmlAttributes::clear(int32_t m)
for (int32_t i = 0; i < length; i++) {
names[i]->release();
names[i] = nullptr;
nsHtml5Portability::releaseString(values[i]);
values[i].Release();
values[i] = nullptr;
}
length = 0;
@ -181,7 +184,7 @@ nsHtml5HtmlAttributes::clear(int32_t m)
void
nsHtml5HtmlAttributes::releaseValue(int32_t i)
{
nsHtml5Portability::releaseString(values[i]);
values[i].Release();
}
void

View File

@ -31,7 +31,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"
@ -64,21 +64,23 @@ class nsHtml5HtmlAttributes
int32_t mode;
int32_t length;
autoJArray<nsHtml5AttributeName*,int32_t> names;
autoJArray<nsString*,int32_t> values;
autoJArray<nsHtml5String, int32_t> values;
autoJArray<int32_t,int32_t> lines;
public:
explicit nsHtml5HtmlAttributes(int32_t mode);
~nsHtml5HtmlAttributes();
int32_t getIndex(nsHtml5AttributeName* name);
nsString* getValue(nsHtml5AttributeName* name);
nsHtml5String getValue(nsHtml5AttributeName* name);
int32_t getLength();
nsIAtom* getLocalNameNoBoundsCheck(int32_t index);
int32_t getURINoBoundsCheck(int32_t index);
nsIAtom* getPrefixNoBoundsCheck(int32_t index);
nsString* getValueNoBoundsCheck(int32_t index);
nsHtml5String getValueNoBoundsCheck(int32_t index);
nsHtml5AttributeName* getAttributeNameNoBoundsCheck(int32_t index);
int32_t getLineNoBoundsCheck(int32_t index);
void addAttribute(nsHtml5AttributeName* name, nsString* value, int32_t line);
void addAttribute(nsHtml5AttributeName* name,
nsHtml5String value,
int32_t line);
void clear(int32_t m);
void releaseValue(int32_t i);
void clearWithoutReleasingContents();

View File

@ -30,7 +30,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"
@ -86,8 +86,8 @@ nsHtml5MetaScanner::nsHtml5MetaScanner(nsHtml5TreeBuilder* tb)
nsHtml5MetaScanner::~nsHtml5MetaScanner()
{
MOZ_COUNT_DTOR(nsHtml5MetaScanner);
nsHtml5Portability::releaseString(content);
nsHtml5Portability::releaseString(charset);
content.Release();
charset.Release();
}
void
@ -771,9 +771,9 @@ bool
nsHtml5MetaScanner::handleTag()
{
bool stop = handleTagInner();
nsHtml5Portability::releaseString(content);
content.Release();
content = nullptr;
nsHtml5Portability::releaseString(charset);
charset.Release();
charset = nullptr;
httpEquivState = NS_HTML5META_SCANNER_HTTP_EQUIV_NOT_SEEN;
return stop;
@ -786,12 +786,13 @@ nsHtml5MetaScanner::handleTagInner()
return true;
}
if (!!content && httpEquivState == NS_HTML5META_SCANNER_HTTP_EQUIV_CONTENT_TYPE) {
nsString* extract = nsHtml5TreeBuilder::extractCharsetFromContent(content, treeBuilder);
nsHtml5String extract =
nsHtml5TreeBuilder::extractCharsetFromContent(content, treeBuilder);
if (!extract) {
return false;
}
bool success = tryCharset(extract);
nsHtml5Portability::releaseString(extract);
extract.Release();
return success;
}
return false;

View File

@ -31,7 +31,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"
@ -76,8 +76,8 @@ class nsHtml5MetaScanner
private:
int32_t strBufLen;
autoJArray<char16_t,int32_t> strBuf;
nsString* content;
nsString* charset;
nsHtml5String content;
nsHtml5String charset;
int32_t httpEquivState;
nsHtml5TreeBuilder* treeBuilder;
public:
@ -100,7 +100,7 @@ class nsHtml5MetaScanner
bool handleTag();
bool handleTagInner();
protected:
bool tryCharset(nsString* encoding);
bool tryCharset(nsHtml5String encoding);
public:
static void initializeStatics();
static void releaseStatics();

View File

@ -19,13 +19,15 @@ nsHtml5MetaScanner::sniff(nsHtml5ByteReadable* bytes, nsACString& charset)
}
bool
nsHtml5MetaScanner::tryCharset(nsString* charset)
nsHtml5MetaScanner::tryCharset(nsHtml5String charset)
{
// This code needs to stay in sync with
// nsHtml5StreamParser::internalEncodingDeclaration. Unfortunately, the
// trickery with member fields here leads to some copy-paste reuse. :-(
nsAutoCString label;
CopyUTF16toUTF8(*charset, label);
nsString charset16; // Not Auto, because using it to hold nsStringBuffer*
charset.ToString(charset16);
CopyUTF16toUTF8(charset16, label);
nsAutoCString encoding;
if (!EncodingUtils::FindEncodingForLabel(label, encoding)) {
return false;

View File

@ -5,21 +5,24 @@
#include "nsHtml5PlainTextUtils.h"
#include "nsHtml5AttributeName.h"
#include "nsHtml5Portability.h"
#include "nsIServiceManager.h"
#include "nsIStringBundle.h"
#include "mozilla/Preferences.h"
#include "nsHtml5String.h"
// static
nsHtml5HtmlAttributes*
nsHtml5PlainTextUtils::NewLinkAttributes()
{
nsHtml5HtmlAttributes* linkAttrs = new nsHtml5HtmlAttributes(0);
nsString* rel = new nsString(NS_LITERAL_STRING("alternate stylesheet"));
nsHtml5String rel =
nsHtml5Portability::newStringFromLiteral("alternate stylesheet");
linkAttrs->addAttribute(nsHtml5AttributeName::ATTR_REL, rel, -1);
nsString* type = new nsString(NS_LITERAL_STRING("text/css"));
nsHtml5String type = nsHtml5Portability::newStringFromLiteral("text/css");
linkAttrs->addAttribute(nsHtml5AttributeName::ATTR_TYPE, type, -1);
nsString* href = new nsString(
NS_LITERAL_STRING("resource://gre-resources/plaintext.css"));
nsHtml5String href = nsHtml5Portability::newStringFromLiteral(
"resource://gre-resources/plaintext.css");
linkAttrs->addAttribute(nsHtml5AttributeName::ATTR_HREF, href, -1);
nsresult rv;
@ -34,7 +37,7 @@ nsHtml5PlainTextUtils::NewLinkAttributes()
bundle->GetStringFromName(u"plainText.wordWrap", getter_Copies(title));
}
nsString* titleCopy = new nsString(title);
linkAttrs->addAttribute(nsHtml5AttributeName::ATTR_TITLE, titleCopy, -1);
linkAttrs->addAttribute(
nsHtml5AttributeName::ATTR_TITLE, nsHtml5String::FromString(title), -1);
return linkAttrs;
}

View File

@ -16,37 +16,31 @@ nsHtml5Portability::newLocalNameFromBuffer(char16_t* buf, int32_t offset, int32_
return interner->GetAtom(nsDependentSubstring(buf, buf + length));
}
nsString*
nsHtml5Portability::newStringFromBuffer(char16_t* buf, int32_t offset, int32_t length, nsHtml5TreeBuilder* treeBuilder)
nsHtml5String
nsHtml5Portability::newStringFromBuffer(char16_t* buf,
int32_t offset,
int32_t length,
nsHtml5TreeBuilder* treeBuilder)
{
nsString* str = new nsString();
bool succeeded = str->Append(buf + offset, length, mozilla::fallible);
if (!succeeded) {
str->Assign(char16_t(0xFFFD));
treeBuilder->MarkAsBroken(NS_ERROR_OUT_OF_MEMORY);
}
return str;
return nsHtml5String::FromBuffer(buf + offset, length, treeBuilder);
}
nsString*
nsHtml5String
nsHtml5Portability::newEmptyString()
{
return new nsString();
return nsHtml5String::EmptyString();
}
nsString*
nsHtml5String
nsHtml5Portability::newStringFromLiteral(const char* literal)
{
nsString* str = new nsString();
str->AssignASCII(literal);
return str;
return nsHtml5String::FromLiteral(literal);
}
nsString*
nsHtml5Portability::newStringFromString(nsString* string) {
nsString* newStr = new nsString();
newStr->Assign(*string);
return newStr;
nsHtml5String
nsHtml5Portability::newStringFromString(nsHtml5String string)
{
return string.Clone();
}
jArray<char16_t,int32_t>
@ -60,12 +54,14 @@ nsHtml5Portability::newCharArrayFromLocal(nsIAtom* local)
return arr;
}
jArray<char16_t,int32_t>
nsHtml5Portability::newCharArrayFromString(nsString* string)
jArray<char16_t, int32_t>
nsHtml5Portability::newCharArrayFromString(nsHtml5String string)
{
int32_t len = string->Length();
MOZ_RELEASE_ASSERT(string);
uint32_t len = string.Length();
MOZ_RELEASE_ASSERT(len < INT32_MAX);
jArray<char16_t,int32_t> arr = jArray<char16_t,int32_t>::newJArray(len);
memcpy(arr, string->BeginReading(), len * sizeof(char16_t));
string.CopyToBuffer(arr);
return arr;
}
@ -82,12 +78,6 @@ nsHtml5Portability::newLocalFromLocal(nsIAtom* local, nsHtml5AtomTable* interner
return local;
}
void
nsHtml5Portability::releaseString(nsString* str)
{
delete str;
}
bool
nsHtml5Portability::localEqualsBuffer(nsIAtom* local, char16_t* buf, int32_t offset, int32_t length)
{
@ -95,55 +85,32 @@ nsHtml5Portability::localEqualsBuffer(nsIAtom* local, char16_t* buf, int32_t off
}
bool
nsHtml5Portability::lowerCaseLiteralIsPrefixOfIgnoreAsciiCaseString(const char* lowerCaseLiteral, nsString* string)
nsHtml5Portability::lowerCaseLiteralIsPrefixOfIgnoreAsciiCaseString(
const char* lowerCaseLiteral,
nsHtml5String string)
{
if (!string) {
return false;
}
const char* litPtr = lowerCaseLiteral;
const char16_t* strPtr = string->BeginReading();
const char16_t* end = string->EndReading();
char16_t litChar;
while ((litChar = *litPtr)) {
NS_ASSERTION(!(litChar >= 'A' && litChar <= 'Z'), "Literal isn't in lower case.");
if (strPtr == end) {
return false;
}
char16_t strChar = *strPtr;
if (strChar >= 'A' && strChar <= 'Z') {
strChar += 0x20;
}
if (litChar != strChar) {
return false;
}
++litPtr;
++strPtr;
}
return true;
return string.LowerCaseStartsWithASCII(lowerCaseLiteral);
}
bool
nsHtml5Portability::lowerCaseLiteralEqualsIgnoreAsciiCaseString(const char* lowerCaseLiteral, nsString* string)
nsHtml5Portability::lowerCaseLiteralEqualsIgnoreAsciiCaseString(
const char* lowerCaseLiteral,
nsHtml5String string)
{
if (!string) {
return false;
}
return string->LowerCaseEqualsASCII(lowerCaseLiteral);
return string.LowerCaseEqualsASCII(lowerCaseLiteral);
}
bool
nsHtml5Portability::literalEqualsString(const char* literal, nsString* string)
nsHtml5Portability::literalEqualsString(const char* literal,
nsHtml5String string)
{
if (!string) {
return false;
}
return string->EqualsASCII(literal);
return string.EqualsASCII(literal);
}
bool
nsHtml5Portability::stringEqualsString(nsString* one, nsString* other)
nsHtml5Portability::stringEqualsString(nsHtml5String one, nsHtml5String other)
{
return one->Equals(*other);
return one.Equals(other);
}
void

View File

@ -30,7 +30,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"
@ -59,19 +59,26 @@ class nsHtml5Portability
{
public:
static nsIAtom* newLocalNameFromBuffer(char16_t* buf, int32_t offset, int32_t length, nsHtml5AtomTable* interner);
static nsString* newStringFromBuffer(char16_t* buf, int32_t offset, int32_t length, nsHtml5TreeBuilder* treeBuilder);
static nsString* newEmptyString();
static nsString* newStringFromLiteral(const char* literal);
static nsString* newStringFromString(nsString* string);
static nsHtml5String newStringFromBuffer(char16_t* buf,
int32_t offset,
int32_t length,
nsHtml5TreeBuilder* treeBuilder);
static nsHtml5String newEmptyString();
static nsHtml5String newStringFromLiteral(const char* literal);
static nsHtml5String newStringFromString(nsHtml5String string);
static jArray<char16_t,int32_t> newCharArrayFromLocal(nsIAtom* local);
static jArray<char16_t,int32_t> newCharArrayFromString(nsString* string);
static jArray<char16_t, int32_t> newCharArrayFromString(
nsHtml5String string);
static nsIAtom* newLocalFromLocal(nsIAtom* local, nsHtml5AtomTable* interner);
static void releaseString(nsString* str);
static bool localEqualsBuffer(nsIAtom* local, char16_t* buf, int32_t offset, int32_t length);
static bool lowerCaseLiteralIsPrefixOfIgnoreAsciiCaseString(const char* lowerCaseLiteral, nsString* string);
static bool lowerCaseLiteralEqualsIgnoreAsciiCaseString(const char* lowerCaseLiteral, nsString* string);
static bool literalEqualsString(const char* literal, nsString* string);
static bool stringEqualsString(nsString* one, nsString* other);
static bool lowerCaseLiteralIsPrefixOfIgnoreAsciiCaseString(
const char* lowerCaseLiteral,
nsHtml5String string);
static bool lowerCaseLiteralEqualsIgnoreAsciiCaseString(
const char* lowerCaseLiteral,
nsHtml5String string);
static bool literalEqualsString(const char* literal, nsHtml5String string);
static bool stringEqualsString(nsHtml5String one, nsHtml5String other);
static void initializeStatics();
static void releaseStatics();
};

View File

@ -35,45 +35,57 @@ class nsHtml5SpeculativeLoad {
nsHtml5SpeculativeLoad();
~nsHtml5SpeculativeLoad();
inline void InitBase(const nsAString& aUrl)
inline void InitBase(nsHtml5String aUrl)
{
NS_PRECONDITION(mOpCode == eSpeculativeLoadUninitialized,
"Trying to reinitialize a speculative load!");
mOpCode = eSpeculativeLoadBase;
mUrl.Assign(aUrl);
aUrl.ToString(mUrl);
}
inline void InitMetaCSP(const nsAString& aCSP) {
inline void InitMetaCSP(nsHtml5String aCSP)
{
NS_PRECONDITION(mOpCode == eSpeculativeLoadUninitialized,
"Trying to reinitialize a speculative load!");
mOpCode = eSpeculativeLoadCSP;
nsString csp; // Not Auto, because using it to hold nsStringBuffer*
aCSP.ToString(csp);
mMetaCSP.Assign(
nsContentUtils::TrimWhitespace<nsContentUtils::IsHTMLWhitespace>(aCSP));
nsContentUtils::TrimWhitespace<nsContentUtils::IsHTMLWhitespace>(csp));
}
inline void InitMetaReferrerPolicy(const nsAString& aReferrerPolicy) {
inline void InitMetaReferrerPolicy(nsHtml5String aReferrerPolicy)
{
NS_PRECONDITION(mOpCode == eSpeculativeLoadUninitialized,
"Trying to reinitialize a speculative load!");
mOpCode = eSpeculativeLoadMetaReferrer;
nsString
referrerPolicy; // Not Auto, because using it to hold nsStringBuffer*
aReferrerPolicy.ToString(referrerPolicy);
mReferrerPolicy.Assign(
nsContentUtils::TrimWhitespace<nsContentUtils::IsHTMLWhitespace>(aReferrerPolicy));
nsContentUtils::TrimWhitespace<nsContentUtils::IsHTMLWhitespace>(
referrerPolicy));
}
inline void InitImage(const nsAString& aUrl,
const nsAString& aCrossOrigin,
const nsAString& aReferrerPolicy,
const nsAString& aSrcset,
const nsAString& aSizes)
inline void InitImage(nsHtml5String aUrl,
nsHtml5String aCrossOrigin,
nsHtml5String aReferrerPolicy,
nsHtml5String aSrcset,
nsHtml5String aSizes)
{
NS_PRECONDITION(mOpCode == eSpeculativeLoadUninitialized,
"Trying to reinitialize a speculative load!");
mOpCode = eSpeculativeLoadImage;
mUrl.Assign(aUrl);
mCrossOrigin.Assign(aCrossOrigin);
aUrl.ToString(mUrl);
aCrossOrigin.ToString(mCrossOrigin);
nsString
referrerPolicy; // Not Auto, because using it to hold nsStringBuffer*
aReferrerPolicy.ToString(referrerPolicy);
mReferrerPolicy.Assign(
nsContentUtils::TrimWhitespace<nsContentUtils::IsHTMLWhitespace>(aReferrerPolicy));
mSrcset.Assign(aSrcset);
mSizes.Assign(aSizes);
nsContentUtils::TrimWhitespace<nsContentUtils::IsHTMLWhitespace>(
referrerPolicy));
aSrcset.ToString(mSrcset);
aSizes.ToString(mSizes);
}
// <picture> elements have multiple <source> nodes followed by an <img>,
@ -97,49 +109,50 @@ class nsHtml5SpeculativeLoad {
mOpCode = eSpeculativeLoadEndPicture;
}
inline void InitPictureSource(const nsAString& aSrcset,
const nsAString& aSizes,
const nsAString& aType,
const nsAString& aMedia)
inline void InitPictureSource(nsHtml5String aSrcset,
nsHtml5String aSizes,
nsHtml5String aType,
nsHtml5String aMedia)
{
NS_PRECONDITION(mOpCode == eSpeculativeLoadUninitialized,
"Trying to reinitialize a speculative load!");
mOpCode = eSpeculativeLoadPictureSource;
mSrcset.Assign(aSrcset);
mSizes.Assign(aSizes);
mTypeOrCharsetSourceOrDocumentMode.Assign(aType);
mMedia.Assign(aMedia);
aSrcset.ToString(mSrcset);
aSizes.ToString(mSizes);
aType.ToString(mTypeOrCharsetSourceOrDocumentMode);
aMedia.ToString(mMedia);
}
inline void InitScript(const nsAString& aUrl,
const nsAString& aCharset,
const nsAString& aType,
const nsAString& aCrossOrigin,
const nsAString& aIntegrity,
inline void InitScript(nsHtml5String aUrl,
nsHtml5String aCharset,
nsHtml5String aType,
nsHtml5String aCrossOrigin,
nsHtml5String aIntegrity,
bool aParserInHead)
{
NS_PRECONDITION(mOpCode == eSpeculativeLoadUninitialized,
"Trying to reinitialize a speculative load!");
mOpCode = aParserInHead ?
eSpeculativeLoadScriptFromHead : eSpeculativeLoadScript;
mUrl.Assign(aUrl);
mCharset.Assign(aCharset);
mTypeOrCharsetSourceOrDocumentMode.Assign(aType);
mCrossOrigin.Assign(aCrossOrigin);
mIntegrity.Assign(aIntegrity);
aUrl.ToString(mUrl);
aCharset.ToString(mCharset);
aType.ToString(mTypeOrCharsetSourceOrDocumentMode);
aCrossOrigin.ToString(mCrossOrigin);
aIntegrity.ToString(mIntegrity);
}
inline void InitStyle(const nsAString& aUrl, const nsAString& aCharset,
const nsAString& aCrossOrigin,
const nsAString& aIntegrity)
inline void InitStyle(nsHtml5String aUrl,
nsHtml5String aCharset,
nsHtml5String aCrossOrigin,
nsHtml5String aIntegrity)
{
NS_PRECONDITION(mOpCode == eSpeculativeLoadUninitialized,
"Trying to reinitialize a speculative load!");
mOpCode = eSpeculativeLoadStyle;
mUrl.Assign(aUrl);
mCharset.Assign(aCharset);
mCrossOrigin.Assign(aCrossOrigin);
mIntegrity.Assign(aIntegrity);
aUrl.ToString(mUrl);
aCharset.ToString(mCharset);
aCrossOrigin.ToString(mCrossOrigin);
aIntegrity.ToString(mIntegrity);
}
/**
@ -153,12 +166,12 @@ class nsHtml5SpeculativeLoad {
* manifests seen by the parser thread have to maintain the queue order
* relative to true speculative loads. See bug 541079.
*/
inline void InitManifest(const nsAString& aUrl)
inline void InitManifest(nsHtml5String aUrl)
{
NS_PRECONDITION(mOpCode == eSpeculativeLoadUninitialized,
"Trying to reinitialize a speculative load!");
mOpCode = eSpeculativeLoadManifest;
mUrl.Assign(aUrl);
aUrl.ToString(mUrl);
}
/**
@ -195,14 +208,13 @@ class nsHtml5SpeculativeLoad {
mTypeOrCharsetSourceOrDocumentMode.Assign((char16_t)aMode);
}
inline void InitPreconnect(const nsAString& aUrl,
const nsAString& aCrossOrigin)
inline void InitPreconnect(nsHtml5String aUrl, nsHtml5String aCrossOrigin)
{
NS_PRECONDITION(mOpCode == eSpeculativeLoadUninitialized,
"Trying to reinitialize a speculative load!");
mOpCode = eSpeculativeLoadPreconnect;
mUrl.Assign(aUrl);
mCrossOrigin.Assign(aCrossOrigin);
aUrl.ToString(mUrl);
aCrossOrigin.ToString(mCrossOrigin);
}
void Perform(nsHtml5TreeOpExecutor* aExecutor);

View File

@ -30,7 +30,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"

View File

@ -31,7 +31,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"

View File

@ -29,7 +29,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"

View File

@ -30,7 +30,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"

View File

@ -1261,7 +1261,7 @@ nsHtml5StreamParser::PreferredForInternalEncodingDecl(nsACString& aEncoding)
}
bool
nsHtml5StreamParser::internalEncodingDeclaration(nsString* aEncoding)
nsHtml5StreamParser::internalEncodingDeclaration(nsHtml5String aEncoding)
{
// This code needs to stay in sync with
// nsHtml5MetaScanner::tryCharset. Unfortunately, the
@ -1270,9 +1270,10 @@ nsHtml5StreamParser::internalEncodingDeclaration(nsString* aEncoding)
if (mCharsetSource >= kCharsetFromMetaTag) { // this threshold corresponds to "confident" in the HTML5 spec
return false;
}
nsString newEncoding16; // Not Auto, because using it to hold nsStringBuffer*
aEncoding.ToString(newEncoding16);
nsAutoCString newEncoding;
CopyUTF16toUTF8(*aEncoding, newEncoding);
CopyUTF16toUTF8(newEncoding16, newEncoding);
if (!PreferredForInternalEncodingDecl(newEncoding)) {
return false;

View File

@ -145,7 +145,7 @@ class nsHtml5StreamParser : public nsICharsetDetectionObserver {
/**
* Tree builder uses this to report a late <meta charset>
*/
bool internalEncodingDeclaration(nsString* aEncoding);
bool internalEncodingDeclaration(nsHtml5String aEncoding);
// Not from an external interface

View File

@ -0,0 +1,226 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "nsHtml5String.h"
#include "nsCharTraits.h"
#include "nsUTF8Utils.h"
#include "nsHtml5TreeBuilder.h"
nsHtml5String::nsHtml5String(already_AddRefed<nsStringBuffer> aBuffer,
uint32_t aLength)
: mBuffer(aBuffer.take())
, mLength(aLength)
{
if (mBuffer) {
MOZ_ASSERT(aLength);
} else {
MOZ_ASSERT(!aLength || aLength == UINT32_MAX);
}
}
void
nsHtml5String::ToString(nsAString& aString)
{
if (mBuffer) {
mBuffer->ToString(mLength, aString);
} else {
aString.Truncate();
if (mLength) {
aString.SetIsVoid(true);
}
}
}
void
nsHtml5String::CopyToBuffer(char16_t* aBuffer)
{
if (mBuffer) {
memcpy(aBuffer, mBuffer->Data(), mLength * sizeof(char16_t));
}
}
bool
nsHtml5String::LowerCaseEqualsASCII(const char* aLowerCaseLiteral)
{
if (!mBuffer) {
if (mLength) {
// This string is null
return false;
}
// this string is empty
return !(*aLowerCaseLiteral);
}
return !nsCharTraits<char16_t>::compareLowerCaseToASCIINullTerminated(
reinterpret_cast<char16_t*>(mBuffer->Data()), Length(), aLowerCaseLiteral);
}
bool
nsHtml5String::EqualsASCII(const char* aLiteral)
{
if (!mBuffer) {
if (mLength) {
// This string is null
return false;
}
// this string is empty
return !(*aLiteral);
}
return !nsCharTraits<char16_t>::compareASCIINullTerminated(
reinterpret_cast<char16_t*>(mBuffer->Data()), Length(), aLiteral);
}
bool
nsHtml5String::LowerCaseStartsWithASCII(const char* aLowerCaseLiteral)
{
if (!mBuffer) {
if (mLength) {
// This string is null
return false;
}
// this string is empty
return !(*aLowerCaseLiteral);
}
const char* litPtr = aLowerCaseLiteral;
const char16_t* strPtr = reinterpret_cast<char16_t*>(mBuffer->Data());
const char16_t* end = strPtr + Length();
char16_t litChar;
while ((litChar = *litPtr) && (strPtr != end)) {
MOZ_ASSERT(!(litChar >= 'A' && litChar <= 'Z'),
"Literal isn't in lower case.");
char16_t strChar = *strPtr;
if (strChar >= 'A' && strChar <= 'Z') {
strChar += 0x20;
}
if (litChar != strChar) {
return false;
}
++litPtr;
++strPtr;
}
return true;
}
bool
nsHtml5String::Equals(nsHtml5String aOther)
{
MOZ_ASSERT(operator bool());
MOZ_ASSERT(aOther);
if (mLength != aOther.mLength) {
return false;
}
if (!mBuffer) {
return true;
}
MOZ_ASSERT(aOther.mBuffer);
return !memcmp(
mBuffer->Data(), aOther.mBuffer->Data(), Length() * sizeof(char16_t));
}
nsHtml5String
nsHtml5String::Clone()
{
MOZ_ASSERT(operator bool());
RefPtr<nsStringBuffer> ref(mBuffer);
return nsHtml5String(ref.forget(), mLength);
}
void
nsHtml5String::Release()
{
if (mBuffer) {
mBuffer->Release();
mBuffer = nullptr;
}
mLength = UINT32_MAX;
}
// static
nsHtml5String
nsHtml5String::FromBuffer(char16_t* aBuffer,
int32_t aLength,
nsHtml5TreeBuilder* aTreeBuilder)
{
if (!aLength) {
return nsHtml5String(nullptr, 0U);
}
// Work with nsStringBuffer directly to make sure that storage is actually
// nsStringBuffer and to make sure the allocation strategy matches
// nsAttrValue::GetStringBuffer, so that it doesn't need to reallocate and
// copy.
RefPtr<nsStringBuffer> buffer(
nsStringBuffer::Alloc((aLength + 1) * sizeof(char16_t)));
if (!buffer) {
if (!aTreeBuilder) {
MOZ_CRASH("Out of memory.");
}
aTreeBuilder->MarkAsBroken(NS_ERROR_OUT_OF_MEMORY);
buffer = nsStringBuffer::Alloc(2 * sizeof(char16_t));
if (!buffer) {
MOZ_CRASH(
"Out of memory so badly that couldn't even allocate placeholder.");
}
char16_t* data = reinterpret_cast<char16_t*>(buffer->Data());
data[0] = 0xFFFD;
data[1] = 0;
return nsHtml5String(buffer.forget(), 1);
}
char16_t* data = reinterpret_cast<char16_t*>(buffer->Data());
memcpy(data, aBuffer, aLength * sizeof(char16_t));
data[aLength] = 0;
return nsHtml5String(buffer.forget(), aLength);
}
// static
nsHtml5String
nsHtml5String::FromLiteral(const char* aLiteral)
{
size_t length = std::strlen(aLiteral);
if (!length) {
return nsHtml5String(nullptr, 0U);
}
// Work with nsStringBuffer directly to make sure that storage is actually
// nsStringBuffer and to make sure the allocation strategy matches
// nsAttrValue::GetStringBuffer, so that it doesn't need to reallocate and
// copy.
RefPtr<nsStringBuffer> buffer(
nsStringBuffer::Alloc((length + 1) * sizeof(char16_t)));
if (!buffer) {
MOZ_CRASH("Out of memory.");
}
char16_t* data = reinterpret_cast<char16_t*>(buffer->Data());
LossyConvertEncoding8to16 converter(data);
converter.write(aLiteral, length);
data[length] = 0;
return nsHtml5String(buffer.forget(), length);
}
// static
nsHtml5String
nsHtml5String::FromString(const nsAString& aString)
{
auto length = aString.Length();
if (!length) {
return nsHtml5String(nullptr, 0U);
}
RefPtr<nsStringBuffer> buffer = nsStringBuffer::FromString(aString);
if (buffer) {
return nsHtml5String(buffer.forget(), length);
}
buffer = nsStringBuffer::Alloc((length + 1) * sizeof(char16_t));
if (!buffer) {
MOZ_CRASH("Out of memory.");
}
char16_t* data = reinterpret_cast<char16_t*>(buffer->Data());
memcpy(data, aString.BeginReading(), length * sizeof(char16_t));
data[length] = 0;
return nsHtml5String(buffer.forget(), length);
}
// static
nsHtml5String
nsHtml5String::EmptyString()
{
return nsHtml5String(nullptr, 0U);
}

View File

@ -0,0 +1,95 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#ifndef nsHtml5String_h
#define nsHtml5String_h
#include "nsString.h"
class nsHtml5TreeBuilder;
/**
* A pass-by-value type that combines an unsafe `nsStringBuffer*` with its
* logical length (`uint32_t`). (`nsStringBuffer` knows its capacity but not
* its logical length, i.e. how much of the capacity is in use.)
*
* Holding or passing this type is as unsafe as holding or passing
* `nsStringBuffer*`.
*
* Empty strings and null strings are distinct. Since an empty nsString does
* not have a an `nsStringBuffer`, both empty and null `nsHtml5String` have
* `nullptr` as `mBuffer`. If `mBuffer` is `nullptr`, the empty case is marked
* with `mLength` being zero and the null case with `mLength` being non-zero.
*/
class nsHtml5String final
{
public:
/**
* Default constructor.
*/
inline nsHtml5String()
: nsHtml5String(nullptr)
{
}
/**
* Constructor from nullptr.
*/
inline MOZ_IMPLICIT nsHtml5String(decltype(nullptr))
: mBuffer(nullptr)
, mLength(UINT32_MAX)
{
}
inline uint32_t Length() const { return mBuffer ? mLength : 0; }
/**
* False iff the string is logically null
*/
inline MOZ_IMPLICIT operator bool() const { return !(!mBuffer && mLength); }
void ToString(nsAString& aString);
void CopyToBuffer(char16_t* aBuffer);
bool LowerCaseEqualsASCII(const char* aLowerCaseLiteral);
bool EqualsASCII(const char* aLiteral);
bool LowerCaseStartsWithASCII(const char* aLowerCaseLiteral);
bool Equals(nsHtml5String aOther);
nsHtml5String Clone();
void Release();
static nsHtml5String FromBuffer(char16_t* aBuffer,
int32_t aLength,
nsHtml5TreeBuilder* aTreeBuilder);
static nsHtml5String FromLiteral(const char* aLiteral);
static nsHtml5String FromString(const nsAString& aString);
static nsHtml5String EmptyString();
private:
/**
* Constructor from raw parts.
*/
nsHtml5String(already_AddRefed<nsStringBuffer> aBuffer, uint32_t aLength);
/**
* nullptr if the string is logically null or logically empty
*/
nsStringBuffer* mBuffer;
/**
* The length of the string. non-zero if the string is logically null.
*/
uint32_t mLength;
};
#endif // nsHtml5String_h

View File

@ -32,7 +32,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"
#include "jArray.h"
@ -113,7 +113,8 @@ nsHtml5Tokenizer::setInterner(nsHtml5AtomTable* interner)
}
void
nsHtml5Tokenizer::initLocation(nsString* newPublicId, nsString* newSystemId)
nsHtml5Tokenizer::initLocation(nsHtml5String newPublicId,
nsHtml5String newSystemId)
{
this->systemId = newSystemId;
this->publicId = newPublicId;
@ -222,10 +223,11 @@ nsHtml5Tokenizer::emitOrAppendCharRefBuf(int32_t returnState)
}
}
nsString*
nsHtml5String
nsHtml5Tokenizer::strBufToString()
{
nsString* str = nsHtml5Portability::newStringFromBuffer(strBuf, 0, strBufLen, tokenHandler);
nsHtml5String str =
nsHtml5Portability::newStringFromBuffer(strBuf, 0, strBufLen, tokenHandler);
clearStrBufAfterUse();
return str;
}
@ -350,7 +352,7 @@ void
nsHtml5Tokenizer::addAttributeWithValue()
{
if (attributeName) {
nsString* val = strBufToString();
nsHtml5String val = strBufToString();
if (mViewSource) {
mViewSource->MaybeLinkifyAttributeValue(attributeName, val);
}
@ -3496,11 +3498,11 @@ nsHtml5Tokenizer::initDoctypeFields()
clearStrBufAfterUse();
doctypeName = nsHtml5Atoms::emptystring;
if (systemIdentifier) {
nsHtml5Portability::releaseString(systemIdentifier);
systemIdentifier.Release();
systemIdentifier = nullptr;
}
if (publicIdentifier) {
nsHtml5Portability::releaseString(publicIdentifier);
publicIdentifier.Release();
publicIdentifier = nullptr;
}
forceQuirks = false;
@ -3662,11 +3664,11 @@ nsHtml5Tokenizer::eof()
errEofInDoctype();
doctypeName = nsHtml5Atoms::emptystring;
if (systemIdentifier) {
nsHtml5Portability::releaseString(systemIdentifier);
systemIdentifier.Release();
systemIdentifier = nullptr;
}
if (publicIdentifier) {
nsHtml5Portability::releaseString(publicIdentifier);
publicIdentifier.Release();
publicIdentifier = nullptr;
}
forceQuirks = true;
@ -3896,14 +3898,14 @@ nsHtml5Tokenizer::emitDoctypeToken(int32_t pos)
cstart = pos + 1;
tokenHandler->doctype(doctypeName, publicIdentifier, systemIdentifier, forceQuirks);
doctypeName = nullptr;
nsHtml5Portability::releaseString(publicIdentifier);
publicIdentifier.Release();
publicIdentifier = nullptr;
nsHtml5Portability::releaseString(systemIdentifier);
systemIdentifier.Release();
systemIdentifier = nullptr;
}
bool
nsHtml5Tokenizer::internalEncodingDeclaration(nsString* internalCharset)
nsHtml5Tokenizer::internalEncodingDeclaration(nsHtml5String internalCharset)
{
if (encodingDeclarationHandler) {
return encodingDeclarationHandler->internalEncodingDeclaration(internalCharset);
@ -3938,11 +3940,11 @@ nsHtml5Tokenizer::end()
strBuf = nullptr;
doctypeName = nullptr;
if (systemIdentifier) {
nsHtml5Portability::releaseString(systemIdentifier);
systemIdentifier.Release();
systemIdentifier = nullptr;
}
if (publicIdentifier) {
nsHtml5Portability::releaseString(publicIdentifier);
publicIdentifier.Release();
publicIdentifier = nullptr;
}
if (tagName) {
@ -4041,13 +4043,13 @@ nsHtml5Tokenizer::loadState(nsHtml5Tokenizer* other)
} else {
doctypeName = nsHtml5Portability::newLocalFromLocal(other->doctypeName, interner);
}
nsHtml5Portability::releaseString(systemIdentifier);
systemIdentifier.Release();
if (!other->systemIdentifier) {
systemIdentifier = nullptr;
} else {
systemIdentifier = nsHtml5Portability::newStringFromString(other->systemIdentifier);
}
nsHtml5Portability::releaseString(publicIdentifier);
publicIdentifier.Release();
if (!other->publicIdentifier) {
publicIdentifier = nullptr;
} else {

View File

@ -33,7 +33,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"
#include "jArray.h"
@ -106,8 +106,8 @@ class nsHtml5Tokenizer
protected:
int32_t cstart;
private:
nsString* publicId;
nsString* systemId;
nsHtml5String publicId;
nsHtml5String systemId;
autoJArray<char16_t,int32_t> strBuf;
int32_t strBufLen;
autoJArray<char16_t,int32_t> charRefBuf;
@ -126,8 +126,8 @@ class nsHtml5Tokenizer
nsHtml5AttributeName* attributeName;
private:
nsIAtom* doctypeName;
nsString* publicIdentifier;
nsString* systemIdentifier;
nsHtml5String publicIdentifier;
nsHtml5String systemIdentifier;
nsHtml5HtmlAttributes* attributes;
bool newAttributesEachTime;
bool shouldSuspend;
@ -141,7 +141,7 @@ class nsHtml5Tokenizer
public:
nsHtml5Tokenizer(nsHtml5TreeBuilder* tokenHandler, bool viewingXmlSource);
void setInterner(nsHtml5AtomTable* interner);
void initLocation(nsString* newPublicId, nsString* newSystemId);
void initLocation(nsHtml5String newPublicId, nsHtml5String newSystemId);
bool isViewingXmlSource();
void setStateAndEndTagExpectation(int32_t specialTokenizerState, nsIAtom* endTagExpectation);
void setStateAndEndTagExpectation(int32_t specialTokenizerState, nsHtml5ElementName* endTagExpectation);
@ -193,7 +193,7 @@ class nsHtml5Tokenizer
}
protected:
nsString* strBufToString();
nsHtml5String strBufToString();
private:
void strBufToDoctypeName();
void emitStrBuf();
@ -285,7 +285,7 @@ class nsHtml5Tokenizer
}
public:
bool internalEncodingDeclaration(nsString* internalCharset);
bool internalEncodingDeclaration(nsHtml5String internalCharset);
private:
void emitOrAppendTwo(const char16_t* val, int32_t returnState);
void emitOrAppendOne(const char16_t* val, int32_t returnState);

View File

@ -34,7 +34,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsITimer.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"
@ -154,13 +154,16 @@ nsHtml5TreeBuilder::startTokenization(nsHtml5Tokenizer* self)
}
void
nsHtml5TreeBuilder::doctype(nsIAtom* name, nsString* publicIdentifier, nsString* systemIdentifier, bool forceQuirks)
nsHtml5TreeBuilder::doctype(nsIAtom* name,
nsHtml5String publicIdentifier,
nsHtml5String systemIdentifier,
bool forceQuirks)
{
needToDropLF = false;
if (!isInForeign() && mode == NS_HTML5TREE_BUILDER_INITIAL) {
nsString* emptyString = nsHtml5Portability::newEmptyString();
nsHtml5String emptyString = nsHtml5Portability::newEmptyString();
appendDoctypeToDocument(!name ? nsHtml5Atoms::emptystring : name, !publicIdentifier ? emptyString : publicIdentifier, !systemIdentifier ? emptyString : systemIdentifier);
nsHtml5Portability::releaseString(emptyString);
emptyString.Release();
if (isQuirky(name, publicIdentifier, systemIdentifier, forceQuirks)) {
errQuirkyDoctype();
documentModeInternal(QUIRKS_MODE, publicIdentifier, systemIdentifier, false);
@ -1990,8 +1993,9 @@ nsHtml5TreeBuilder::isSpecialParentInForeign(nsHtml5StackNode* stackNode)
return (kNameSpaceID_XHTML == ns) || (stackNode->isHtmlIntegrationPoint()) || ((kNameSpaceID_MathML == ns) && (stackNode->getGroup() == NS_HTML5TREE_BUILDER_MI_MO_MN_MS_MTEXT));
}
nsString*
nsHtml5TreeBuilder::extractCharsetFromContent(nsString* attributeValue, nsHtml5TreeBuilder* tb)
nsHtml5String
nsHtml5TreeBuilder::extractCharsetFromContent(nsHtml5String attributeValue,
nsHtml5TreeBuilder* tb)
{
int32_t charsetState = NS_HTML5TREE_BUILDER_CHARSET_INITIAL;
int32_t start = -1;
@ -2175,12 +2179,13 @@ nsHtml5TreeBuilder::extractCharsetFromContent(nsString* attributeValue, nsHtml5T
}
}
charsetloop_end: ;
nsString* charset = nullptr;
nsHtml5String charset = nullptr;
if (start != -1) {
if (end == -1) {
end = buffer.length;
}
charset = nsHtml5Portability::newStringFromBuffer(buffer, start, end - start, tb);
charset =
nsHtml5Portability::newStringFromBuffer(buffer, start, end - start, tb);
}
return charset;
}
@ -2188,7 +2193,8 @@ nsHtml5TreeBuilder::extractCharsetFromContent(nsString* attributeValue, nsHtml5T
void
nsHtml5TreeBuilder::checkMetaCharset(nsHtml5HtmlAttributes* attributes)
{
nsString* charset = attributes->getValue(nsHtml5AttributeName::ATTR_CHARSET);
nsHtml5String charset =
attributes->getValue(nsHtml5AttributeName::ATTR_CHARSET);
if (charset) {
if (tokenizer->internalEncodingDeclaration(charset)) {
requestSuspension();
@ -2199,15 +2205,17 @@ nsHtml5TreeBuilder::checkMetaCharset(nsHtml5HtmlAttributes* attributes)
if (!nsHtml5Portability::lowerCaseLiteralEqualsIgnoreAsciiCaseString("content-type", attributes->getValue(nsHtml5AttributeName::ATTR_HTTP_EQUIV))) {
return;
}
nsString* content = attributes->getValue(nsHtml5AttributeName::ATTR_CONTENT);
nsHtml5String content =
attributes->getValue(nsHtml5AttributeName::ATTR_CONTENT);
if (content) {
nsString* extract = nsHtml5TreeBuilder::extractCharsetFromContent(content, this);
nsHtml5String extract =
nsHtml5TreeBuilder::extractCharsetFromContent(content, this);
if (extract) {
if (tokenizer->internalEncodingDeclaration(extract)) {
requestSuspension();
}
}
nsHtml5Portability::releaseString(extract);
extract.Release();
}
}
@ -3208,7 +3216,11 @@ nsHtml5TreeBuilder::isSecondOnStackBody()
}
void
nsHtml5TreeBuilder::documentModeInternal(nsHtml5DocumentMode m, nsString* publicIdentifier, nsString* systemIdentifier, bool html4SpecificAdditionalErrorChecks)
nsHtml5TreeBuilder::documentModeInternal(
nsHtml5DocumentMode m,
nsHtml5String publicIdentifier,
nsHtml5String systemIdentifier,
bool html4SpecificAdditionalErrorChecks)
{
if (isSrcdocDocument) {
quirks = false;
@ -3220,7 +3232,8 @@ nsHtml5TreeBuilder::documentModeInternal(nsHtml5DocumentMode m, nsString* public
}
bool
nsHtml5TreeBuilder::isAlmostStandards(nsString* publicIdentifier, nsString* systemIdentifier)
nsHtml5TreeBuilder::isAlmostStandards(nsHtml5String publicIdentifier,
nsHtml5String systemIdentifier)
{
if (nsHtml5Portability::lowerCaseLiteralEqualsIgnoreAsciiCaseString("-//w3c//dtd xhtml 1.0 transitional//en", publicIdentifier)) {
return true;
@ -3240,7 +3253,10 @@ nsHtml5TreeBuilder::isAlmostStandards(nsString* publicIdentifier, nsString* syst
}
bool
nsHtml5TreeBuilder::isQuirky(nsIAtom* name, nsString* publicIdentifier, nsString* systemIdentifier, bool forceQuirks)
nsHtml5TreeBuilder::isQuirky(nsIAtom* name,
nsHtml5String publicIdentifier,
nsHtml5String systemIdentifier,
bool forceQuirks)
{
if (forceQuirks) {
return true;
@ -4051,7 +4067,8 @@ nsHtml5TreeBuilder::appendToCurrentNodeAndPushElementMayFosterMathML(nsHtml5Elem
bool
nsHtml5TreeBuilder::annotationXmlEncodingPermitsHtml(nsHtml5HtmlAttributes* attributes)
{
nsString* encoding = attributes->getValue(nsHtml5AttributeName::ATTR_ENCODING);
nsHtml5String encoding =
attributes->getValue(nsHtml5AttributeName::ATTR_ENCODING);
if (!encoding) {
return false;
}

View File

@ -35,7 +35,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsITimer.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"
@ -103,7 +103,10 @@ class nsHtml5TreeBuilder : public nsAHtml5TreeBuilderState
bool isSrcdocDocument;
public:
void startTokenization(nsHtml5Tokenizer* self);
void doctype(nsIAtom* name, nsString* publicIdentifier, nsString* systemIdentifier, bool forceQuirks);
void doctype(nsIAtom* name,
nsHtml5String publicIdentifier,
nsHtml5String systemIdentifier,
bool forceQuirks);
void comment(char16_t* buf, int32_t start, int32_t length);
void characters(const char16_t* buf, int32_t start, int32_t length);
void zeroOriginatingReplacementCharacter();
@ -119,7 +122,8 @@ class nsHtml5TreeBuilder : public nsAHtml5TreeBuilderState
bool isTemplateModeStackEmpty();
bool isSpecialParentInForeign(nsHtml5StackNode* stackNode);
public:
static nsString* extractCharsetFromContent(nsString* attributeValue, nsHtml5TreeBuilder* tb);
static nsHtml5String extractCharsetFromContent(nsHtml5String attributeValue,
nsHtml5TreeBuilder* tb);
private:
void checkMetaCharset(nsHtml5HtmlAttributes* attributes);
public:
@ -136,9 +140,16 @@ class nsHtml5TreeBuilder : public nsAHtml5TreeBuilderState
void generateImpliedEndTagsExceptFor(nsIAtom* name);
void generateImpliedEndTags();
bool isSecondOnStackBody();
void documentModeInternal(nsHtml5DocumentMode m, nsString* publicIdentifier, nsString* systemIdentifier, bool html4SpecificAdditionalErrorChecks);
bool isAlmostStandards(nsString* publicIdentifier, nsString* systemIdentifier);
bool isQuirky(nsIAtom* name, nsString* publicIdentifier, nsString* systemIdentifier, bool forceQuirks);
void documentModeInternal(nsHtml5DocumentMode m,
nsHtml5String publicIdentifier,
nsHtml5String systemIdentifier,
bool html4SpecificAdditionalErrorChecks);
bool isAlmostStandards(nsHtml5String publicIdentifier,
nsHtml5String systemIdentifier);
bool isQuirky(nsIAtom* name,
nsHtml5String publicIdentifier,
nsHtml5String systemIdentifier,
bool forceQuirks);
void closeTheCell(int32_t eltPos);
int32_t findLastInTableScopeTdTh();
void clearStackBackTo(int32_t eltPos);
@ -224,7 +235,9 @@ class nsHtml5TreeBuilder : public nsAHtml5TreeBuilderState
void markMalformedIfScript(nsIContentHandle* elt);
void start(bool fragmentMode);
void end();
void appendDoctypeToDocument(nsIAtom* name, nsString* publicIdentifier, nsString* systemIdentifier);
void appendDoctypeToDocument(nsIAtom* name,
nsHtml5String publicIdentifier,
nsHtml5String systemIdentifier);
void elementPushed(int32_t ns, nsIAtom* name, nsIContentHandle* node);
void elementPopped(int32_t ns, nsIAtom* name, nsIContentHandle* node);
public:

View File

@ -123,181 +123,178 @@ nsHtml5TreeBuilder::createElement(int32_t aNamespace, nsIAtom* aName,
switch (aNamespace) {
case kNameSpaceID_XHTML:
if (nsHtml5Atoms::img == aName) {
nsString* url = aAttributes->getValue(nsHtml5AttributeName::ATTR_SRC);
nsString* srcset =
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_SRC);
nsHtml5String srcset =
aAttributes->getValue(nsHtml5AttributeName::ATTR_SRCSET);
nsString* crossOrigin =
nsHtml5String crossOrigin =
aAttributes->getValue(nsHtml5AttributeName::ATTR_CROSSORIGIN);
nsString* referrerPolicy =
nsHtml5String referrerPolicy =
aAttributes->getValue(nsHtml5AttributeName::ATTR_REFERRERPOLICY);
nsString* sizes =
nsHtml5String sizes =
aAttributes->getValue(nsHtml5AttributeName::ATTR_SIZES);
mSpeculativeLoadQueue.AppendElement()->
InitImage(url ? *url : NullString(),
crossOrigin ? *crossOrigin : NullString(),
referrerPolicy ? *referrerPolicy : NullString(),
srcset ? *srcset : NullString(),
sizes ? *sizes : NullString());
mSpeculativeLoadQueue.AppendElement()->InitImage(
url, crossOrigin, referrerPolicy, srcset, sizes);
} else if (nsHtml5Atoms::source == aName) {
nsString* srcset =
nsHtml5String srcset =
aAttributes->getValue(nsHtml5AttributeName::ATTR_SRCSET);
// Sources without srcset cannot be selected. The source could also be
// for a media element, but in that context doesn't use srcset. See
// comments in nsHtml5SpeculativeLoad.h about <picture> preloading
if (srcset) {
nsString* sizes =
nsHtml5String sizes =
aAttributes->getValue(nsHtml5AttributeName::ATTR_SIZES);
nsString* type =
nsHtml5String type =
aAttributes->getValue(nsHtml5AttributeName::ATTR_TYPE);
nsString* media =
nsHtml5String media =
aAttributes->getValue(nsHtml5AttributeName::ATTR_MEDIA);
mSpeculativeLoadQueue.AppendElement()->
InitPictureSource(*srcset,
sizes ? *sizes : NullString(),
type ? *type : NullString(),
media ? *media : NullString());
mSpeculativeLoadQueue.AppendElement()->InitPictureSource(
srcset, sizes, type, media);
}
} else if (nsHtml5Atoms::script == aName) {
nsHtml5TreeOperation* treeOp = mOpQueue.AppendElement();
NS_ASSERTION(treeOp, "Tree op allocation failed.");
treeOp->Init(eTreeOpSetScriptLineNumberAndFreeze, content, tokenizer->getLineNumber());
nsString* url = aAttributes->getValue(nsHtml5AttributeName::ATTR_SRC);
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_SRC);
if (url) {
nsString* charset = aAttributes->getValue(nsHtml5AttributeName::ATTR_CHARSET);
nsString* type = aAttributes->getValue(nsHtml5AttributeName::ATTR_TYPE);
nsString* crossOrigin =
nsHtml5String charset =
aAttributes->getValue(nsHtml5AttributeName::ATTR_CHARSET);
nsHtml5String type =
aAttributes->getValue(nsHtml5AttributeName::ATTR_TYPE);
nsHtml5String crossOrigin =
aAttributes->getValue(nsHtml5AttributeName::ATTR_CROSSORIGIN);
nsString* integrity =
nsHtml5String integrity =
aAttributes->getValue(nsHtml5AttributeName::ATTR_INTEGRITY);
mSpeculativeLoadQueue.AppendElement()->
InitScript(*url,
(charset) ? *charset : EmptyString(),
(type) ? *type : EmptyString(),
(crossOrigin) ? *crossOrigin : NullString(),
(integrity) ? *integrity : NullString(),
mode == NS_HTML5TREE_BUILDER_IN_HEAD);
mSpeculativeLoadQueue.AppendElement()->InitScript(
url,
charset,
type,
crossOrigin,
integrity,
mode == NS_HTML5TREE_BUILDER_IN_HEAD);
mCurrentHtmlScriptIsAsyncOrDefer =
aAttributes->contains(nsHtml5AttributeName::ATTR_ASYNC) ||
aAttributes->contains(nsHtml5AttributeName::ATTR_DEFER);
}
} else if (nsHtml5Atoms::link == aName) {
nsString* rel = aAttributes->getValue(nsHtml5AttributeName::ATTR_REL);
nsHtml5String rel =
aAttributes->getValue(nsHtml5AttributeName::ATTR_REL);
// Not splitting on space here is bogus but the old parser didn't even
// do a case-insensitive check.
if (rel) {
if (rel->LowerCaseEqualsASCII("stylesheet")) {
nsString* url = aAttributes->getValue(nsHtml5AttributeName::ATTR_HREF);
if (rel.LowerCaseEqualsASCII("stylesheet")) {
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_HREF);
if (url) {
nsString* charset = aAttributes->getValue(nsHtml5AttributeName::ATTR_CHARSET);
nsString* crossOrigin =
nsHtml5String charset =
aAttributes->getValue(nsHtml5AttributeName::ATTR_CHARSET);
nsHtml5String crossOrigin =
aAttributes->getValue(nsHtml5AttributeName::ATTR_CROSSORIGIN);
nsString* integrity =
nsHtml5String integrity =
aAttributes->getValue(nsHtml5AttributeName::ATTR_INTEGRITY);
mSpeculativeLoadQueue.AppendElement()->
InitStyle(*url,
(charset) ? *charset : EmptyString(),
(crossOrigin) ? *crossOrigin : NullString(),
(integrity) ? *integrity : NullString());
mSpeculativeLoadQueue.AppendElement()->InitStyle(
url, charset, crossOrigin, integrity);
}
} else if (rel->LowerCaseEqualsASCII("preconnect")) {
nsString* url = aAttributes->getValue(nsHtml5AttributeName::ATTR_HREF);
} else if (rel.LowerCaseEqualsASCII("preconnect")) {
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_HREF);
if (url) {
nsString* crossOrigin =
nsHtml5String crossOrigin =
aAttributes->getValue(nsHtml5AttributeName::ATTR_CROSSORIGIN);
mSpeculativeLoadQueue.AppendElement()->
InitPreconnect(*url, (crossOrigin) ? *crossOrigin : NullString());
mSpeculativeLoadQueue.AppendElement()->InitPreconnect(
url, crossOrigin);
}
}
}
} else if (nsHtml5Atoms::video == aName) {
nsString* url = aAttributes->getValue(nsHtml5AttributeName::ATTR_POSTER);
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_POSTER);
if (url) {
mSpeculativeLoadQueue.AppendElement()->InitImage(*url, NullString(),
NullString(),
NullString(),
NullString());
mSpeculativeLoadQueue.AppendElement()->InitImage(
url, nullptr, nullptr, nullptr, nullptr);
}
} else if (nsHtml5Atoms::style == aName) {
nsHtml5TreeOperation* treeOp = mOpQueue.AppendElement();
NS_ASSERTION(treeOp, "Tree op allocation failed.");
treeOp->Init(eTreeOpSetStyleLineNumber, content, tokenizer->getLineNumber());
} else if (nsHtml5Atoms::html == aName) {
nsString* url = aAttributes->getValue(nsHtml5AttributeName::ATTR_MANIFEST);
if (url) {
mSpeculativeLoadQueue.AppendElement()->InitManifest(*url);
} else {
mSpeculativeLoadQueue.AppendElement()->InitManifest(EmptyString());
}
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_MANIFEST);
mSpeculativeLoadQueue.AppendElement()->InitManifest(url);
} else if (nsHtml5Atoms::base == aName) {
nsString* url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_HREF);
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_HREF);
if (url) {
mSpeculativeLoadQueue.AppendElement()->InitBase(*url);
mSpeculativeLoadQueue.AppendElement()->InitBase(url);
}
} else if (nsHtml5Atoms::meta == aName) {
if (nsHtml5Portability::lowerCaseLiteralEqualsIgnoreAsciiCaseString(
"content-security-policy",
aAttributes->getValue(nsHtml5AttributeName::ATTR_HTTP_EQUIV))) {
nsString* csp = aAttributes->getValue(nsHtml5AttributeName::ATTR_CONTENT);
nsHtml5String csp =
aAttributes->getValue(nsHtml5AttributeName::ATTR_CONTENT);
if (csp) {
mSpeculativeLoadQueue.AppendElement()->InitMetaCSP(*csp);
mSpeculativeLoadQueue.AppendElement()->InitMetaCSP(csp);
}
}
else if (nsHtml5Portability::lowerCaseLiteralEqualsIgnoreAsciiCaseString(
"referrer",
aAttributes->getValue(nsHtml5AttributeName::ATTR_NAME))) {
nsString* referrerPolicy = aAttributes->getValue(nsHtml5AttributeName::ATTR_CONTENT);
nsHtml5String referrerPolicy =
aAttributes->getValue(nsHtml5AttributeName::ATTR_CONTENT);
if (referrerPolicy) {
mSpeculativeLoadQueue.AppendElement()->InitMetaReferrerPolicy(*referrerPolicy);
mSpeculativeLoadQueue.AppendElement()->InitMetaReferrerPolicy(
referrerPolicy);
}
}
}
break;
case kNameSpaceID_SVG:
if (nsHtml5Atoms::image == aName) {
nsString* url = aAttributes->getValue(nsHtml5AttributeName::ATTR_XLINK_HREF);
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_XLINK_HREF);
if (url) {
mSpeculativeLoadQueue.AppendElement()->InitImage(*url, NullString(),
NullString(),
NullString(),
NullString());
mSpeculativeLoadQueue.AppendElement()->InitImage(
url, nullptr, nullptr, nullptr, nullptr);
}
} else if (nsHtml5Atoms::script == aName) {
nsHtml5TreeOperation* treeOp = mOpQueue.AppendElement();
NS_ASSERTION(treeOp, "Tree op allocation failed.");
treeOp->Init(eTreeOpSetScriptLineNumberAndFreeze, content, tokenizer->getLineNumber());
nsString* url = aAttributes->getValue(nsHtml5AttributeName::ATTR_XLINK_HREF);
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_XLINK_HREF);
if (url) {
nsString* type = aAttributes->getValue(nsHtml5AttributeName::ATTR_TYPE);
nsString* crossOrigin =
nsHtml5String type =
aAttributes->getValue(nsHtml5AttributeName::ATTR_TYPE);
nsHtml5String crossOrigin =
aAttributes->getValue(nsHtml5AttributeName::ATTR_CROSSORIGIN);
nsString* integrity =
nsHtml5String integrity =
aAttributes->getValue(nsHtml5AttributeName::ATTR_INTEGRITY);
mSpeculativeLoadQueue.AppendElement()->
InitScript(*url,
EmptyString(),
(type) ? *type : EmptyString(),
(crossOrigin) ? *crossOrigin : NullString(),
(integrity) ? *integrity : NullString(),
mode == NS_HTML5TREE_BUILDER_IN_HEAD);
mSpeculativeLoadQueue.AppendElement()->InitScript(
url,
nullptr,
type,
crossOrigin,
integrity,
mode == NS_HTML5TREE_BUILDER_IN_HEAD);
}
} else if (nsHtml5Atoms::style == aName) {
nsHtml5TreeOperation* treeOp = mOpQueue.AppendElement();
NS_ASSERTION(treeOp, "Tree op allocation failed.");
treeOp->Init(eTreeOpSetStyleLineNumber, content, tokenizer->getLineNumber());
nsString* url = aAttributes->getValue(nsHtml5AttributeName::ATTR_XLINK_HREF);
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_XLINK_HREF);
if (url) {
nsString* crossOrigin =
nsHtml5String crossOrigin =
aAttributes->getValue(nsHtml5AttributeName::ATTR_CROSSORIGIN);
nsString* integrity =
nsHtml5String integrity =
aAttributes->getValue(nsHtml5AttributeName::ATTR_INTEGRITY);
mSpeculativeLoadQueue.AppendElement()->
InitStyle(*url, EmptyString(),
(crossOrigin) ? *crossOrigin : NullString(),
(integrity) ? *integrity : NullString());
mSpeculativeLoadQueue.AppendElement()->InitStyle(
url, nullptr, crossOrigin, integrity);
}
}
break;
@ -320,18 +317,23 @@ nsHtml5TreeBuilder::createElement(int32_t aNamespace, nsIAtom* aName,
}
} else if (aNamespace == kNameSpaceID_XHTML) {
if (nsHtml5Atoms::html == aName) {
nsString* url = aAttributes->getValue(nsHtml5AttributeName::ATTR_MANIFEST);
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_MANIFEST);
nsHtml5TreeOperation* treeOp = mOpQueue.AppendElement();
NS_ASSERTION(treeOp, "Tree op allocation failed.");
if (url) {
treeOp->Init(eTreeOpProcessOfflineManifest, *url);
nsString
urlString; // Not Auto, because using it to hold nsStringBuffer*
url.ToString(urlString);
treeOp->Init(eTreeOpProcessOfflineManifest, urlString);
} else {
treeOp->Init(eTreeOpProcessOfflineManifest, EmptyString());
}
} else if (nsHtml5Atoms::base == aName && mViewSource) {
nsString* url = aAttributes->getValue(nsHtml5AttributeName::ATTR_HREF);
nsHtml5String url =
aAttributes->getValue(nsHtml5AttributeName::ATTR_HREF);
if (url) {
mViewSource->AddBase(*url);
mViewSource->AddBase(url);
}
}
}
@ -743,17 +745,19 @@ nsHtml5TreeBuilder::end()
}
void
nsHtml5TreeBuilder::appendDoctypeToDocument(nsIAtom* aName, nsString* aPublicId, nsString* aSystemId)
nsHtml5TreeBuilder::appendDoctypeToDocument(nsIAtom* aName,
nsHtml5String aPublicId,
nsHtml5String aSystemId)
{
NS_PRECONDITION(aName, "Null name");
nsString publicId; // Not Auto, because using it to hold nsStringBuffer*
nsString systemId; // Not Auto, because using it to hold nsStringBuffer*
aPublicId.ToString(publicId);
aSystemId.ToString(systemId);
if (mBuilder) {
nsCOMPtr<nsIAtom> name = nsHtml5TreeOperation::Reget(aName);
nsresult rv =
nsHtml5TreeOperation::AppendDoctypeToDocument(name,
*aPublicId,
*aSystemId,
mBuilder);
nsresult rv = nsHtml5TreeOperation::AppendDoctypeToDocument(
name, publicId, systemId, mBuilder);
if (NS_FAILED(rv)) {
MarkAsBrokenAndRequestSuspension(rv);
}
@ -762,7 +766,7 @@ nsHtml5TreeBuilder::appendDoctypeToDocument(nsIAtom* aName, nsString* aPublicId,
nsHtml5TreeOperation* treeOp = mOpQueue.AppendElement();
NS_ASSERTION(treeOp, "Tree op allocation failed.");
treeOp->Init(aName, *aPublicId, *aSystemId);
treeOp->Init(aName, publicId, systemId);
// nsXMLContentSink can flush here, but what's the point?
// It can also interrupt here, but we can't.
}

View File

@ -319,11 +319,10 @@ nsHtml5TreeOperation::AddAttributes(nsIContent* aNode,
if (!node->HasAttr(nsuri, localName)) {
// prefix doesn't need regetting. it is always null or a static atom
// local name is never null
node->SetAttr(nsuri,
localName,
aAttributes->getPrefixNoBoundsCheck(i),
*(aAttributes->getValueNoBoundsCheck(i)),
true);
nsString value; // Not Auto, because using it to hold nsStringBuffer*
aAttributes->getValueNoBoundsCheck(i).ToString(value);
node->SetAttr(
nsuri, localName, aAttributes->getPrefixNoBoundsCheck(i), value, true);
// XXX what to do with nsresult?
}
}
@ -418,12 +417,14 @@ nsHtml5TreeOperation::CreateElement(int32_t aNs,
nsCOMPtr<nsIAtom> prefix = aAttributes->getPrefixNoBoundsCheck(i);
int32_t nsuri = aAttributes->getURINoBoundsCheck(i);
nsString value; // Not Auto, because using it to hold nsStringBuffer*
aAttributes->getValueNoBoundsCheck(i).ToString(value);
if (aNs == kNameSpaceID_XHTML &&
nsHtml5Atoms::a == aName &&
nsHtml5Atoms::name == localName) {
// This is an HTML5-incompliant Geckoism.
// Remove when fixing bug 582361
NS_ConvertUTF16toUTF8 cname(*(aAttributes->getValueNoBoundsCheck(i)));
NS_ConvertUTF16toUTF8 cname(value);
NS_ConvertUTF8toUTF16 uv(nsUnescape(cname.BeginWriting()));
newContent->SetAttr(nsuri,
localName,
@ -431,7 +432,6 @@ nsHtml5TreeOperation::CreateElement(int32_t aNs,
uv,
false);
} else {
nsString& value = *(aAttributes->getValueNoBoundsCheck(i));
newContent->SetAttr(nsuri,
localName,
prefix,

View File

@ -29,7 +29,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"

View File

@ -30,7 +30,7 @@
#include "nsIAtom.h"
#include "nsHtml5AtomTable.h"
#include "nsString.h"
#include "nsHtml5String.h"
#include "nsNameSpaceManager.h"
#include "nsIContent.h"
#include "nsTraceRefcnt.h"

View File

@ -6,32 +6,35 @@
#include "nsHtml5ViewSourceUtils.h"
#include "nsHtml5AttributeName.h"
#include "mozilla/Preferences.h"
#include "mozilla/UniquePtr.h"
#include "nsHtml5String.h"
// static
nsHtml5HtmlAttributes*
nsHtml5ViewSourceUtils::NewBodyAttributes()
{
nsHtml5HtmlAttributes* bodyAttrs = new nsHtml5HtmlAttributes(0);
auto id = MakeUnique<nsString>(NS_LITERAL_STRING("viewsource"));
bodyAttrs->addAttribute(nsHtml5AttributeName::ATTR_ID, id.release(), -1);
nsHtml5String id = nsHtml5Portability::newStringFromLiteral("viewsource");
bodyAttrs->addAttribute(nsHtml5AttributeName::ATTR_ID, id, -1);
auto klass = MakeUnique<nsString>();
nsString klass;
if (mozilla::Preferences::GetBool("view_source.wrap_long_lines", true)) {
klass->Append(NS_LITERAL_STRING("wrap "));
klass.Append(NS_LITERAL_STRING("wrap "));
}
if (mozilla::Preferences::GetBool("view_source.syntax_highlight", true)) {
klass->Append(NS_LITERAL_STRING("highlight"));
klass.Append(NS_LITERAL_STRING("highlight"));
}
if (!klass->IsEmpty()) {
bodyAttrs->addAttribute(nsHtml5AttributeName::ATTR_CLASS, klass.release(), -1);
if (!klass.IsEmpty()) {
bodyAttrs->addAttribute(
nsHtml5AttributeName::ATTR_CLASS, nsHtml5String::FromString(klass), -1);
}
int32_t tabSize = mozilla::Preferences::GetInt("view_source.tab_size", 4);
if (tabSize > 0) {
auto style = MakeUnique<nsString>(NS_LITERAL_STRING("-moz-tab-size: "));
style->AppendInt(tabSize);
bodyAttrs->addAttribute(nsHtml5AttributeName::ATTR_STYLE, style.release(), -1);
nsString style;
style.AssignASCII("-moz-tab-size: ");
style.AppendInt(tabSize);
bodyAttrs->addAttribute(
nsHtml5AttributeName::ATTR_STYLE, nsHtml5String::FromString(style), -1);
}
return bodyAttrs;
@ -42,12 +45,12 @@ nsHtml5HtmlAttributes*
nsHtml5ViewSourceUtils::NewLinkAttributes()
{
nsHtml5HtmlAttributes* linkAttrs = new nsHtml5HtmlAttributes(0);
nsString* rel = new nsString(NS_LITERAL_STRING("stylesheet"));
nsHtml5String rel = nsHtml5Portability::newStringFromLiteral("stylesheet");
linkAttrs->addAttribute(nsHtml5AttributeName::ATTR_REL, rel, -1);
nsString* type = new nsString(NS_LITERAL_STRING("text/css"));
nsHtml5String type = nsHtml5Portability::newStringFromLiteral("text/css");
linkAttrs->addAttribute(nsHtml5AttributeName::ATTR_TYPE, type, -1);
nsString* href = new nsString(
NS_LITERAL_STRING("resource://gre-resources/viewsource.css"));
nsHtml5String href = nsHtml5Portability::newStringFromLiteral(
"resource://gre-resources/viewsource.css");
linkAttrs->addAttribute(nsHtml5AttributeName::ATTR_HREF, href, -1);
return linkAttrs;
}