Fixed a crash my making sure that the CNavDTD and HTMLContentSink stacks are synchronized when handling a FORM. b=133410, r=heikki, sr=jst

git-svn-id: svn://10.0.0.236/trunk@118812 18797224-902f-48f8-a5cc-f745e15eee43
This commit is contained in:
harishd%netscape.com
2002-04-11 23:50:44 +00:00
parent c5dc75cf4b
commit 4737cceba4
14 changed files with 69 additions and 47 deletions

View File

@@ -336,6 +336,13 @@ public:
*/
NS_IMETHOD NotifyTagObservers(nsIParserNode* aNode)=0;
/**
* Call this method to determnine if a FORM is on the sink's stack
*
* @return PR_TRUE if found else PR_FALSE
*/
NS_IMETHOD_(PRBool) IsFormOnStack() = 0;
};
#ifdef NS_DEBUG
@@ -345,3 +352,4 @@ extern nsresult NS_NewHTMLNullSink(nsIContentSink** aInstancePtrResult);
#endif
#endif /* nsIHTMLContentSink_h___ */

View File

@@ -90,6 +90,8 @@ public:
NS_IMETHOD OpenFrameset(const nsIParserNode& aNode);
NS_IMETHOD CloseFrameset(const nsIParserNode& aNode);
NS_IMETHOD GetPref(PRInt32 aTag,PRBool& aPref) { return NS_OK; }
NS_IMETHOD_(PRBool) IsFormOnStack() { return PR_FALSE; }
NS_IMETHOD OpenContainer(const nsIParserNode& aNode);
NS_IMETHOD CloseContainer(const nsIParserNode& aNode);
NS_IMETHOD CloseTopmostContainer();

View File

@@ -117,7 +117,6 @@ static char gShowCRC;
#define NS_DTD_FLAG_HAD_FRAMESET 0x00000010
#define NS_DTD_FLAG_ENABLE_RESIDUAL_STYLE 0x00000020
#define NS_DTD_FLAG_REQUESTED_HEAD 0x00000040
#define NS_DTD_FLAG_IS_FORM_CONTAINER 0x00000080
#define NS_DTD_FLAG_SCRIPT_ENABLED 0x00000100
#define NS_DTD_FLAG_FRAMES_ENABLED 0x00000200
#define NS_DTD_FLAG_ALTERNATE_CONTENT 0x00000400 // NOFRAMES, NOSCRIPT
@@ -579,7 +578,7 @@ nsresult CNavDTD::DidBuildModel(nsresult anErrorCode,PRBool aNotifySink,nsIParse
result=HandleToken(theTableToken,mParser);
}
}
if(result==NS_OK) {
if(NS_SUCCEEDED(result)) {
eHTMLTags theTarget;
//now let's disable style handling to save time when closing remaining stack members...
@@ -2034,14 +2033,15 @@ nsresult CNavDTD::HandleSavedTokens(PRInt32 anIndex) {
PRInt32 attrCount;
PRInt32 theTopIndex = anIndex + 1;
PRInt32 theTagCount = mBodyContext->GetCount();
//eHTMLTags theParentTag= mBodyContext->TagAt(anIndex);
//XXX In the content sink, FORM behaves as a container for parents
//other than eHTMLTag_table,eHTMLTag_tbody,eHTMLTag_tr,eHTMLTag_col,
//eHTMLTag_tfoot,eHTMLTag_thead,eHTMLTag_colgroup.In those cases the stack
//position, in the parser, should be synchronized with the sink. -- Ref: Bug 20087.
if (!(~mFlags & (NS_DTD_FLAG_HAS_OPEN_FORM | NS_DTD_FLAG_IS_FORM_CONTAINER))) anIndex++;
if (mSink && mSink->IsFormOnStack()) {
// Do this to synchronize dtd stack and the sink stack.
// Note: FORM is never on the dtd stack because its always
// considered as a leaf. However, in the sink FORM can either
// be a container or a leaf. Therefore, we have to check
// with the sink -- Ref: Bug 20087.
anIndex++;
}
STOP_TIMER()
MOZ_TIMER_DEBUGLOG(("Stop: Parse Time: CNavDTD::HandleSavedTokensAbove(), this=%p\n", this));
@@ -3188,18 +3188,8 @@ nsresult CNavDTD::CloseBody(const nsIParserNode *aNode){
* @return TRUE if ok, FALSE if error
*/
nsresult CNavDTD::OpenForm(const nsIParserNode *aNode){
static eHTMLTags gTableElements[]={eHTMLTag_table,eHTMLTag_tbody,eHTMLTag_tr,
eHTMLTag_tfoot,eHTMLTag_thead,
eHTMLTag_col,eHTMLTag_colgroup};
nsresult result=NS_OK;
if(!(mFlags & NS_DTD_FLAG_HAS_OPEN_FORM)) { // discard nested forms - bug 72639
// Check if the parent is a table, tbody, thead, tfoot, tr, col or
// colgroup. If so, treat form as a leaf content. [ Ex. bug 92530 ]
if(!FindTagInSet(mBodyContext->Last(),gTableElements,
sizeof(gTableElements)/sizeof(eHTMLTag_unknown))) {
mFlags |= NS_DTD_FLAG_IS_FORM_CONTAINER;
}
STOP_TIMER();
MOZ_TIMER_DEBUGLOG(("Stop: Parse Time: CNavDTD::OpenForm(), this=%p\n", this));
@@ -3238,8 +3228,6 @@ nsresult CNavDTD::CloseForm(const nsIParserNode *aNode){
MOZ_TIMER_DEBUGLOG(("Start: Parse Time: CNavDTD::CloseForm(), this=%p\n", this));
START_TIMER();
mFlags &= ~NS_DTD_FLAG_IS_FORM_CONTAINER;
}
return result;
}

View File

@@ -88,6 +88,8 @@ public:
NS_IMETHOD OpenFrameset(const nsIParserNode& aNode);
NS_IMETHOD CloseFrameset(const nsIParserNode& aNode);
NS_IMETHOD GetPref(PRInt32 aTag,PRBool& aPref) { return NS_OK; }
NS_IMETHOD_(PRBool) IsFormOnStack() { return PR_FALSE; }
NS_IMETHOD WillProcessTokens(void) { return NS_OK; }
NS_IMETHOD DidProcessTokens(void) { return NS_OK; }
NS_IMETHOD WillProcessAToken(void) { return NS_OK; }

View File

@@ -630,6 +630,7 @@ nsresult nsHTMLTokenizer::ConsumeAttributes(PRUnichar aChar,
PRBool isUsableAttr = PR_TRUE;
const nsAString& key=theToken->GetKey();
const nsAString& text=theToken->GetValue();
// support XML like syntax to fix bugs like 44186
if(!key.IsEmpty() && kForwardSlash==key.First() && text.IsEmpty()) {
isUsableAttr = PRBool(mFlags & NS_IPARSER_FLAG_VIEW_SOURCE); // Fix bug 103095

View File

@@ -91,6 +91,8 @@ public:
NS_IMETHOD OpenFrameset(const nsIParserNode& aNode);
NS_IMETHOD CloseFrameset(const nsIParserNode& aNode);
NS_IMETHOD GetPref(PRInt32 aTag,PRBool& aPref) { return NS_OK; }
NS_IMETHOD_(PRBool) IsFormOnStack() { return PR_FALSE; }
NS_IMETHOD DoFragment(PRBool aFlag);
NS_IMETHOD BeginContext(PRInt32 aPosition);
NS_IMETHOD EndContext(PRInt32 aPosition);
@@ -119,3 +121,4 @@ protected:
};
#endif