added DTD and propagation capabilities; dynamic entities, containers, token handlers

This commit is contained in:
rickg 1998-04-22 18:32:49 +00:00
Родитель 60d933a6cb
Коммит c11fa9da39
60 изменённых файлов: 5726 добавлений и 836 удалений

298
htmlparser/src/CNavDTD.cpp Normal file
Просмотреть файл

@ -0,0 +1,298 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/8/98
*
*
*/
#include "CNavDTD.h"
#include "nsHTMLTokens.h"
#include "nsCRT.h"
#include "nsParserTypes.h"
static NS_DEFINE_IID(kISupportsIID, NS_ISUPPORTS_IID);
static NS_DEFINE_IID(kIDTDIID, NS_IDTD_IID);
static NS_DEFINE_IID(kHTMLDTDIID, NS_IHTML_DTD_IID);
static NS_DEFINE_IID(kClassIID, NS_INAVHTML_DTD_IID);
/**-------------------------------------------------------
* This method gets called as part of our COM-like interfaces.
* Its purpose is to create an interface to parser object
* of some type.
*
* @update gess 4/8/98
* @param nsIID id of object to discover
* @param aInstancePtr ptr to newly discovered interface
* @return NS_xxx result code
*------------------------------------------------------*/
nsresult CNavDTD::QueryInterface(const nsIID& aIID, void** aInstancePtr)
{
if (NULL == aInstancePtr) {
return NS_ERROR_NULL_POINTER;
}
if(aIID.Equals(kISupportsIID)) { //do IUnknown...
*aInstancePtr = (nsIDTD*)(this);
}
else if(aIID.Equals(kIDTDIID)) { //do IParser base class...
*aInstancePtr = (nsIDTD*)(this);
}
else if(aIID.Equals(kClassIID)) { //do this class...
*aInstancePtr = (CNavDTD*)(this);
}
else {
*aInstancePtr=0;
return NS_NOINTERFACE;
}
((nsISupports*) *aInstancePtr)->AddRef();
return NS_OK;
}
/**-------------------------------------------------------
* This method is defined in nsIParser. It is used to
* cause the COM-like construction of an nsHTMLParser.
*
* @update gess 4/8/98
* @param nsIParser** ptr to newly instantiated parser
* @return NS_xxx error result
*------------------------------------------------------*/
NS_HTMLPARS nsresult NS_NewNavHTMLDTD(nsIDTD** aInstancePtrResult)
{
CNavDTD* it = new CNavDTD();
if (it == 0) {
return NS_ERROR_OUT_OF_MEMORY;
}
return it->QueryInterface(kClassIID, (void **) aInstancePtrResult);
}
NS_IMPL_ADDREF(CNavDTD)
NS_IMPL_RELEASE(CNavDTD)
/**-------------------------------------------------------
* Default constructor
*
* @update gess 4/9/98
* @param
* @return
*------------------------------------------------------*/
CNavDTD::CNavDTD() : nsHTMLDTD() {
}
/**-------------------------------------------------------
* Default destructor
*
* @update gess 4/9/98
* @param
* @return
*------------------------------------------------------*/
CNavDTD::~CNavDTD(){
}
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 4/8/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
PRBool CNavDTD::CanContain(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=nsHTMLDTD::CanContain(aParent,aChild);
return result;
}
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 4/8/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
PRBool CNavDTD::CanContainIndirect(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=nsHTMLDTD::CanContainIndirect(aParent,aChild);
return result;
}
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag can contain newlines. Most do not.
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
PRBool CNavDTD::CanOmit(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=PR_FALSE;
switch((eHTMLTags)aParent) {
case eHTMLTag_tr:
case eHTMLTag_table:
case eHTMLTag_thead:
case eHTMLTag_tfoot:
case eHTMLTag_tbody:
case eHTMLTag_col:
case eHTMLTag_colgroup:
if((aChild==eHTMLTag_newline) ||
(aChild==eHTMLTag_whitespace))
result=PR_TRUE;
break;
default:
result=PR_FALSE;
break;
}
return result;
}
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag is itself a container
*
* @update gess 4/8/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
PRBool CNavDTD::IsContainer(PRInt32 aTag) const {
PRBool result=nsHTMLDTD::IsContainer(aTag);
return result;
}
/*-------------------------------------------------------
* This method does two things: 1st, help construct
* our own internal model of the content-stack; and
* 2nd, pass this message on to the sink.
* @update gess4/6/98
* @param aNode -- next node to be added to model
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRInt32 CNavDTD::GetDefaultParentTagFor(PRInt32 aTag) const{
eHTMLTags result=eHTMLTag_unknown;
switch(aTag) {
case eHTMLTag_html:
result=(eHTMLTags)kNotFound; break;
case eHTMLTag_body:
case eHTMLTag_head:
case eHTMLTag_header:
case eHTMLTag_footer:
case eHTMLTag_frameset:
result=eHTMLTag_html; break;
//These tags are head specific...
case eHTMLTag_style:
case eHTMLTag_meta:
case eHTMLTag_title:
case eHTMLTag_base:
case eHTMLTag_link:
result=eHTMLTag_head; break;
//These tags are table specific...
case eHTMLTag_caption:
case eHTMLTag_colgroup:
case eHTMLTag_tbody:
case eHTMLTag_tfoot:
case eHTMLTag_thead:
case eHTMLTag_tr:
result=eHTMLTag_table; break;
case eHTMLTag_td:
case eHTMLTag_th:
result=eHTMLTag_tr; break;
case eHTMLTag_col:
result=eHTMLTag_colgroup; break;
//These have to do with listings...
case eHTMLTag_listitem:
result=eHTMLTag_ul; break;
case eHTMLTag_dd:
case eHTMLTag_dt:
result=eHTMLTag_dl; break;
case eHTMLTag_option:
result=eHTMLTag_select; break;
//These have to do with image maps...
case eHTMLTag_area:
result=eHTMLTag_map; break;
//These have to do with applets...
case eHTMLTag_param:
result=eHTMLTag_applet; break;
//These have to do with frames...
case eHTMLTag_frame:
result=eHTMLTag_frameset; break;
default:
result=eHTMLTag_body; //XXX Hack! Just for now.
break;
}
return result;
}
/** ------------------------------------------------------
* This method gets called at various times by the parser
* whenever we want to verify a valid context stack. This
* method also gives us a hook to add debugging metrics.
*
* @update gess4/6/98
* @param aStack[] array of ints (tokens)
* @param aCount number of elements in given array
* @return TRUE if stack is valid, else FALSE
*/ //-----------------------------------------------------
PRBool CNavDTD::VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const {
PRBool result=PR_TRUE;
if(aCount>0) {
}
return result;
}
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
PRInt32 CNavDTD::CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const {
PRInt32 result=0;
return result;
}

147
htmlparser/src/CNavDTD.h Normal file
Просмотреть файл

@ -0,0 +1,147 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/8/98
*
*
*/
#ifndef NS_NAVHTMLDTD__
#define NS_NAVHTMLDTD__
#include "nsHTMLDTD.h"
#include "nsHTMLTokens.h"
#include "nshtmlpars.h"
#define NS_INAVHTML_DTD_IID \
{0x5c5cce40, 0xcfd6, 0x11d1, \
{0xaa, 0xda, 0x00, 0x80, 0x5f, 0x8a, 0x3e, 0x14}}
class CNavDTD : public nsHTMLDTD {
public:
NS_DECL_ISUPPORTS
/** -------------------------------------------------------
*
*
* @update gess 4/9/98
* @param
* @return
*/ //------------------------------------------------------
CNavDTD();
/** -------------------------------------------------------
*
*
* @update gess 4/9/98
* @param
* @return
*/ //------------------------------------------------------
virtual ~CNavDTD();
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 3/25/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
virtual PRBool CanContain(PRInt32 aParent,PRInt32 aChild) const;
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 3/25/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
virtual PRBool CanContainIndirect(PRInt32 aParent,PRInt32 aChild) const;
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag can contain newlines. Most do not.
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool CanOmit(PRInt32 aParent,PRInt32 aChild)const;
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag is itself a container
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool IsContainer(PRInt32 aTags) const;
/** ------------------------------------------------------
* This method does two things: 1st, help construct
* our own internal model of the content-stack; and
* 2nd, pass this message on to the sink.
* @update gess4/6/98
* @param aNode -- next node to be added to model
* @return TRUE if ok, FALSE if error
*/ //----------------------------------------------------
virtual PRInt32 GetDefaultParentTagFor(PRInt32 aTag) const;
/** ------------------------------------------------------
* This method gets called at various times by the parser
* whenever we want to verify a valid context stack. This
* method also gives us a hook to add debugging metrics.
*
* @update gess4/6/98
* @param aStack[] array of ints (tokens)
* @param aCount number of elements in given array
* @return TRUE if stack is valid, else FALSE
*/ //-----------------------------------------------------
virtual PRBool VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const;
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
virtual PRInt32 CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const;
};
#endif

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

@ -0,0 +1,232 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
#include <ctype.h>
#include "CNavDelegate.h"
#include "nsHTMLTokens.h"
#include "nsScanner.h"
#include "nsParserTypes.h"
// Note: We already handle the following special case conditions:
// 1) If you see </>, simply treat it as a bad tag.
// 2) If you see </ ...>, treat it like a comment.
// 3) If you see <> or <_ (< space) simply treat it as text.
// 4) If you see <~ (< followed by non-alpha), treat it as text.
static char gIdentChars[] = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_";
/**-------------------------------------------------------
* Default constructor
*
* @updated gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
CNavDelegate::CNavDelegate() : CHTMLTokenizerDelegate(){
}
/**-------------------------------------------------------
* Default constructor
*
* @updated gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
CNavDelegate::CNavDelegate(CNavDelegate& aDelegate) : CHTMLTokenizerDelegate() {
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
eParseMode CNavDelegate::GetParseMode() const {
return eParseMode_navigator;
}
/**-------------------------------------------------------
* This method is called just after a "<" has been consumed
* and we know we're at the start of some kind of tagged
* element. We don't know yet if it's a tag or a comment.
*
* @update gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
CToken* CNavDelegate::ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CToken* result=0;
nsAutoString empty("");
anErrorCode=anErrorCode=aScanner.GetChar(aChar);
switch(aChar) {
case kForwardSlash:
PRUnichar ch;
anErrorCode=aScanner.Peek(ch);
if(nsString::IsAlpha(ch))
result=new CEndToken(empty);
else result=new CCommentToken(empty); //Special case: </ ...> is treated as a comment
break;
case kExclamation:
result=new CCommentToken(empty);
break;
default:
if(nsString::IsAlpha(aChar))
return ConsumeStartTag(aChar,aScanner,anErrorCode);
else if(kNotFound!=aChar) {
nsAutoString temp("<");
return ConsumeText(temp,aScanner,anErrorCode);
}
}
if(result!=0) {
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(anErrorCode) {
result=0;
delete result;
}
}
return result;
}
/*-------------------------------------------------------
* This is a special case method. It's job is to consume
* all of the given tag up to an including the end tag.
*
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* CNavDelegate::ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode){
//In the case that we just read the given tag, we should go and
//consume all the input until we find a matching end tag.
nsAutoString endTag("</");
endTag.Append(aString);
endTag.Append(">");
CSkippedContentToken* sc=new CSkippedContentToken(endTag);
anErrorCode= sc->Consume(aChar,aScanner); //tell new token to finish consuming text...
return sc;
}
/**-------------------------------------------------------
* This method is called just after a "<" has been consumed
* and we know we're at the start of a tag.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* CNavDelegate::ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CStartToken* result=new CStartToken(nsAutoString(""));
if(result) {
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(result->IsAttributed())
ConsumeAttributes(aChar,aScanner,anErrorCode);
//now that that's over with, we have one more problem to solve.
//In the case that we just read a <SCRIPT> or <STYLE> tags, we should go and
//consume all the content itself.
nsString& str=result->GetText();
if(str.EqualsIgnoreCase("SCRIPT") ||
str.EqualsIgnoreCase("STYLE") ||
str.EqualsIgnoreCase("TITLE")) {
CToken* sc=ConsumeContentToEndTag(str,aChar,aScanner,anErrorCode);
if(sc){
//now we strip the ending sequence from our new SkippedContent token...
PRInt32 slen=str.Length()+3;
nsString& skippedText=sc->GetText();
skippedText.Cut(skippedText.Length()-slen,slen);
mTokenDeque.Push(sc);
//In the case that we just read a given tag, we should go and
//consume all the tag content itself (and throw it all away).
CEndToken* endtoken=new CEndToken(str);
mTokenDeque.Push(endtoken);
}
}
}
return result;
}
/**-------------------------------------------------------
* This method is called just after a "&" has been consumed
* and we know we're at the start of an entity.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* CNavDelegate::ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CToken* result = 0;
PRUnichar ch;
anErrorCode=aScanner.GetChar(ch);
if(nsString::IsAlpha(ch)) { //handle common enity references &xxx; or &#000.
result = new CEntityToken(nsAutoString(""));
anErrorCode= result->Consume(ch,aScanner); //tell new token to finish consuming text...
}
else if(kHashsign==ch) {
result = new CEntityToken(nsAutoString(""));
anErrorCode=result->Consume(ch,aScanner);
}
else
{
//oops, we're actually looking at plain text...
nsAutoString temp("&");
return ConsumeText(temp,aScanner,anErrorCode);
}
return result;
}
/**-------------------------------------------------------
* This method repeatedly called by the tokenizer.
* Each time, we determine the kind of token were about to
* read, and then we call the appropriate method to handle
* that token type.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* CNavDelegate::GetToken(CScanner& aScanner,PRInt32& anErrorCode) {
return CHTMLTokenizerDelegate::GetToken(aScanner,anErrorCode);
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
CToken* CNavDelegate::CreateTokenOfType(eHTMLTokenTypes aType) {
return 0;
}

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

@ -0,0 +1,70 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/1/98
*
* This class is used as the HTML tokenizer delegate for
* netscape navigator compatibility.
*
* The tokenzier class has the smarts to open an source,
* and iterate over its characters to produce a list of
* tokens. The tokenizer doesn't know HTML, which is
* where this delegate comes into play.
*
* The tokenizer calls methods on this class to help
* with the creation of HTML-specific tokens from a source
* stream.
*
* The interface here is very simple, mainly the call
* to GetToken(), which Consumes bytes from the underlying
* scanner.stream, and produces an HTML specific CToken.
*/
#ifndef __NAV_DELEGATE
#define __NAV_DELEGATE
#include "nsToken.h"
#include "nsHTMLDelegate.h"
class CNavDelegate : public CHTMLTokenizerDelegate {
public:
CNavDelegate();
CNavDelegate(CNavDelegate& aDelegate);
virtual CToken* GetToken(CScanner& aScanner,PRInt32& anErrorCode);
virtual eParseMode GetParseMode() const;
protected:
virtual CToken* ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
//the only special case method...
virtual CToken* ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* CreateTokenOfType(eHTMLTokenTypes aType);
};
#endif

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

@ -0,0 +1,298 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/8/98
*
*
*/
#include "COtherDTD.h"
#include "nsHTMLTokens.h"
#include "nsCRT.h"
#include "nsParserTypes.h"
static NS_DEFINE_IID(kISupportsIID, NS_ISUPPORTS_IID);
static NS_DEFINE_IID(kIDTDIID, NS_IDTD_IID);
static NS_DEFINE_IID(kHTMLDTDIID, NS_IHTML_DTD_IID);
static NS_DEFINE_IID(kClassIID, NS_IOtherHTML_DTD_IID);
/**-------------------------------------------------------
* This method gets called as part of our COM-like interfaces.
* Its purpose is to create an interface to parser object
* of some type.
*
* @update gess 4/8/98
* @param nsIID id of object to discover
* @param aInstancePtr ptr to newly discovered interface
* @return NS_xxx result code
*------------------------------------------------------*/
nsresult COtherDTD::QueryInterface(const nsIID& aIID, void** aInstancePtr)
{
if (NULL == aInstancePtr) {
return NS_ERROR_NULL_POINTER;
}
if(aIID.Equals(kISupportsIID)) { //do IUnknown...
*aInstancePtr = (nsIDTD*)(this);
}
else if(aIID.Equals(kIDTDIID)) { //do IParser base class...
*aInstancePtr = (nsIDTD*)(this);
}
else if(aIID.Equals(kClassIID)) { //do this class...
*aInstancePtr = (COtherDTD*)(this);
}
else {
*aInstancePtr=0;
return NS_NOINTERFACE;
}
((nsISupports*) *aInstancePtr)->AddRef();
return NS_OK;
}
/**-------------------------------------------------------
* This method is defined in nsIParser. It is used to
* cause the COM-like construction of an nsHTMLParser.
*
* @update gess 4/8/98
* @param nsIParser** ptr to newly instantiated parser
* @return NS_xxx error result
*------------------------------------------------------*/
NS_HTMLPARS nsresult NS_NewOtherHTMLDTD(nsIDTD** aInstancePtrResult)
{
COtherDTD* it = new COtherDTD();
if (it == 0) {
return NS_ERROR_OUT_OF_MEMORY;
}
return it->QueryInterface(kClassIID, (void **) aInstancePtrResult);
}
NS_IMPL_ADDREF(COtherDTD)
NS_IMPL_RELEASE(COtherDTD)
/**-------------------------------------------------------
* Default constructor
*
* @update gess 4/9/98
* @param
* @return
*------------------------------------------------------*/
COtherDTD::COtherDTD() : nsHTMLDTD() {
}
/**-------------------------------------------------------
* Default destructor
*
* @update gess 4/9/98
* @param
* @return
*------------------------------------------------------*/
COtherDTD::~COtherDTD(){
}
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 4/8/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
PRBool COtherDTD::CanContain(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=nsHTMLDTD::CanContain(aParent,aChild);
return result;
}
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 4/8/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
PRBool COtherDTD::CanContainIndirect(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=nsHTMLDTD::CanContainIndirect(aParent,aChild);
return result;
}
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag can contain newlines. Most do not.
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
PRBool COtherDTD::CanOmit(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=PR_FALSE;
switch((eHTMLTags)aParent) {
case eHTMLTag_tr:
case eHTMLTag_table:
case eHTMLTag_thead:
case eHTMLTag_tfoot:
case eHTMLTag_tbody:
case eHTMLTag_col:
case eHTMLTag_colgroup:
if((aChild==eHTMLTag_newline) ||
(aChild==eHTMLTag_whitespace))
result=PR_TRUE;
break;
default:
result=PR_FALSE;
break;
}
return result;
}
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag is itself a container
*
* @update gess 4/8/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
PRBool COtherDTD::IsContainer(PRInt32 aTag) const {
PRBool result=nsHTMLDTD::IsContainer(aTag);
return result;
}
/*-------------------------------------------------------
* This method does two things: 1st, help construct
* our own internal model of the content-stack; and
* 2nd, pass this message on to the sink.
* @update gess4/6/98
* @param aNode -- next node to be added to model
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRInt32 COtherDTD::GetDefaultParentTagFor(PRInt32 aTag) const{
eHTMLTags result=eHTMLTag_unknown;
switch(aTag) {
case eHTMLTag_html:
result=(eHTMLTags)kNotFound; break;
case eHTMLTag_body:
case eHTMLTag_head:
case eHTMLTag_header:
case eHTMLTag_footer:
case eHTMLTag_frameset:
result=eHTMLTag_html; break;
//These tags are head specific...
case eHTMLTag_style:
case eHTMLTag_meta:
case eHTMLTag_title:
case eHTMLTag_base:
case eHTMLTag_link:
result=eHTMLTag_head; break;
//These tags are table specific...
case eHTMLTag_caption:
case eHTMLTag_colgroup:
case eHTMLTag_tbody:
case eHTMLTag_tfoot:
case eHTMLTag_thead:
case eHTMLTag_tr:
result=eHTMLTag_table; break;
case eHTMLTag_td:
case eHTMLTag_th:
result=eHTMLTag_tr; break;
case eHTMLTag_col:
result=eHTMLTag_colgroup; break;
//These have to do with listings...
case eHTMLTag_listitem:
result=eHTMLTag_ul; break;
case eHTMLTag_dd:
case eHTMLTag_dt:
result=eHTMLTag_dl; break;
case eHTMLTag_option:
result=eHTMLTag_select; break;
//These have to do with image maps...
case eHTMLTag_area:
result=eHTMLTag_map; break;
//These have to do with applets...
case eHTMLTag_param:
result=eHTMLTag_applet; break;
//These have to do with frames...
case eHTMLTag_frame:
result=eHTMLTag_frameset; break;
default:
result=eHTMLTag_body; //XXX Hack! Just for now.
break;
}
return result;
}
/** ------------------------------------------------------
* This method gets called at various times by the parser
* whenever we want to verify a valid context stack. This
* method also gives us a hook to add debugging metrics.
*
* @update gess4/6/98
* @param aStack[] array of ints (tokens)
* @param aCount number of elements in given array
* @return TRUE if stack is valid, else FALSE
*/ //-----------------------------------------------------
PRBool COtherDTD::VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const {
PRBool result=PR_TRUE;
if(aCount>0) {
}
return result;
}
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
PRInt32 COtherDTD::CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const {
PRInt32 result=0;
return result;
}

148
htmlparser/src/COtherDTD.h Normal file
Просмотреть файл

@ -0,0 +1,148 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/8/98
*
*
*/
#ifndef NS_OTHERHTMLDTD__
#define NS_OTHERHTMLDTD__
#include "nsHTMLDTD.h"
#include "nsHTMLTokens.h"
#include "nshtmlpars.h"
#define NS_IOtherHTML_DTD_IID \
{0x8a5e89c0, 0xd16d, 0x11d1, \
{0x80, 0x22, 0x00, 0x60, 0x8, 0x14, 0x98, 0x89}}
class COtherDTD : public nsHTMLDTD {
public:
NS_DECL_ISUPPORTS
/** -------------------------------------------------------
*
*
* @update gess 4/9/98
* @param
* @return
*/ //------------------------------------------------------
COtherDTD();
/** -------------------------------------------------------
*
*
* @update gess 4/9/98
* @param
* @return
*/ //------------------------------------------------------
virtual ~COtherDTD();
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 3/25/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
virtual PRBool CanContain(PRInt32 aParent,PRInt32 aChild) const;
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 3/25/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
virtual PRBool CanContainIndirect(PRInt32 aParent,PRInt32 aChild) const;
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag can contain newlines. Most do not.
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool CanOmit(PRInt32 aParent,PRInt32 aChild)const;
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag is itself a container
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool IsContainer(PRInt32 aTags) const;
/** ------------------------------------------------------
* This method does two things: 1st, help construct
* our own internal model of the content-stack; and
* 2nd, pass this message on to the sink.
* @update gess4/6/98
* @param aNode -- next node to be added to model
* @return TRUE if ok, FALSE if error
*/ //----------------------------------------------------
virtual PRInt32 GetDefaultParentTagFor(PRInt32 aTag) const;
/** ------------------------------------------------------
* This method gets called at various times by the parser
* whenever we want to verify a valid context stack. This
* method also gives us a hook to add debugging metrics.
*
* @update gess4/6/98
* @param aStack[] array of ints (tokens)
* @param aCount number of elements in given array
* @return TRUE if stack is valid, else FALSE
*/ //-----------------------------------------------------
virtual PRBool VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const;
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
virtual PRInt32 CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const;
};
#endif

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

@ -0,0 +1,235 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
#include <ctype.h>
#include "COtherDelegate.h"
#include "nsHTMLTokens.h"
#include "nsScanner.h"
#include "nsParserTypes.h"
// Note: We already handle the following special case conditions:
// 1) If you see </>, simply treat it as a bad tag.
// 2) If you see </ ...>, treat it like a comment.
// 3) If you see <> or <_ (< space) simply treat it as text.
// 4) If you see <~ (< followed by non-alpha), treat it as text.
static char gIdentChars[] = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_";
/**-------------------------------------------------------
* Default constructor
*
* @updated gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
COtherDelegate::COtherDelegate() : CHTMLTokenizerDelegate(){
}
/**-------------------------------------------------------
* Default constructor
*
* @updated gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
COtherDelegate::COtherDelegate(COtherDelegate& aDelegate) : CHTMLTokenizerDelegate(){
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
eParseMode COtherDelegate::GetParseMode() const {
return eParseMode_other;
}
/**-------------------------------------------------------
* This method is called just after a "<" has been consumed
* and we know we're at the start of some kind of tagged
* element. We don't know yet if it's a tag or a comment.
*
* @update gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
CToken* COtherDelegate::ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CToken* result=0;
nsAutoString empty("");
anErrorCode=anErrorCode=aScanner.GetChar(aChar);
switch(aChar) {
case kForwardSlash:
PRUnichar ch;
anErrorCode=aScanner.Peek(ch);
if(nsString::IsAlpha(ch))
result=new CEndToken(empty);
else result=new CCommentToken(empty); //Special case: </ ...> is treated as a comment
break;
case kExclamation:
result=new CCommentToken(empty);
break;
default:
if(nsString::IsAlpha(aChar))
return ConsumeStartTag(aChar,aScanner,anErrorCode);
else if(kNotFound!=aChar) {
nsAutoString temp("<");
return ConsumeText(temp,aScanner,anErrorCode);
}
}
if(result!=0) {
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(anErrorCode) {
result=0;
delete result;
}
}
return result;
}
/*-------------------------------------------------------
* This is a special case method. It's job is to consume
* all of the given tag up to an including the end tag.
*
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* COtherDelegate::ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode){
//In the case that we just read the given tag, we should go and
//consume all the input until we find a matching end tag.
nsAutoString endTag("</");
endTag.Append(aString);
endTag.Append(">");
CSkippedContentToken* sc=new CSkippedContentToken(endTag);
anErrorCode= sc->Consume(aChar,aScanner); //tell new token to finish consuming text...
return sc;
}
/**-------------------------------------------------------
* This method is called just after a "<" has been consumed
* and we know we're at the start of a tag.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* COtherDelegate::ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CStartToken* result=new CStartToken(nsAutoString(""));
if(result) {
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(result->IsAttributed())
ConsumeAttributes(aChar,aScanner,anErrorCode);
//now that that's over with, we have one more problem to solve.
//In the case that we just read a <SCRIPT> or <STYLE> tags, we should go and
//consume all the content itself.
nsString& str=result->GetText();
if(str.EqualsIgnoreCase("SCRIPT") ||
str.EqualsIgnoreCase("STYLE") ||
str.EqualsIgnoreCase("TITLE")) {
CToken* sc=ConsumeContentToEndTag(str,aChar,aScanner,anErrorCode);
if(sc){
//now we strip the ending sequence from our new SkippedContent token...
PRInt32 slen=str.Length()+3;
nsString& skippedText=sc->GetText();
skippedText.Cut(skippedText.Length()-slen,slen);
mTokenDeque.Push(sc);
//In the case that we just read a given tag, we should go and
//consume all the tag content itself (and throw it all away).
CEndToken* endtoken=new CEndToken(str);
mTokenDeque.Push(endtoken);
}
}
}
return result;
}
/**-------------------------------------------------------
* This method is called just after a "&" has been consumed
* and we know we're at the start of an entity.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* COtherDelegate::ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CToken* result = 0;
PRUnichar ch;
anErrorCode=aScanner.GetChar(ch);
if(nsString::IsAlpha(ch)) { //handle common enity references &xxx; or &#000.
result = new CEntityToken(nsAutoString(""));
anErrorCode= result->Consume(ch,aScanner); //tell new token to finish consuming text...
}
else if(kHashsign==ch) {
result = new CEntityToken(nsAutoString(""));
anErrorCode=result->Consume(ch,aScanner);
}
else
{
//oops, we're actually looking at plain text...
nsAutoString temp("&");
return ConsumeText(temp,aScanner,anErrorCode);
}
return result;
}
/**-------------------------------------------------------
* This method repeatedly called by the tokenizer.
* Each time, we determine the kind of token were about to
* read, and then we call the appropriate method to handle
* that token type.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* COtherDelegate::GetToken(CScanner& aScanner,PRInt32& anErrorCode){
return CHTMLTokenizerDelegate::GetToken(aScanner,anErrorCode);
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
CToken* COtherDelegate::CreateTokenOfType(eHTMLTokenTypes aType) {
return 0;
}

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

@ -0,0 +1,71 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/1/98
*
* This class is used as the HTML tokenizer delegate for
* an alternate html browser.
*
* The tokenzier class has the smarts to open an source,
* and iterate over its characters to produce a list of
* tokens. The tokenizer doesn't know HTML, which is
* where this delegate comes into play.
*
* The tokenizer calls methods on this class to help
* with the creation of HTML-specific tokens from a source
* stream.
*
* The interface here is very simple, mainly the call
* to GetToken(), which Consumes bytes from the underlying
* scanner.stream, and produces an HTML specific CToken.
*/
#ifndef __OTHER_DELEGATE
#define __OTHER_DELEGATE
#include "nsToken.h"
#include "nsHTMLDelegate.h"
class COtherDelegate : public CHTMLTokenizerDelegate {
public:
COtherDelegate();
COtherDelegate(COtherDelegate& aDelegate);
virtual CToken* GetToken(CScanner& aScanner,PRInt32& anErrorCode);
virtual eParseMode GetParseMode() const;
protected:
virtual CToken* ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
//the only special case method...
virtual CToken* ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* CreateTokenOfType(eHTMLTokenTypes aType);
};
#endif

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

@ -22,17 +22,20 @@ LIBRARY_NAME = raptorhtmlpars
DEFINES = -D_IMPL_NS_HTMLPARS
CPPSRCS = \
nsDeque.cpp \
nsHTMLContentSink.cpp \
nsHTMLDelegate.cpp \
nsHTMLParser.cpp \
nsHTMLTokens.cpp \
nsParserNode.cpp \
nsScanner.cpp \
nsToken.cpp \
nsTokenizer.cpp \
nsDefaultTokenHandler.cpp \
nsTokenHandler.cpp \
nsHTMLParser.cpp \
nsHTMLTokens.cpp \
nsHTMLDelegate.cpp \
nsHTMLDTD.cpp \
CNavDelegate.cpp \
CNavDTD.cpp \
COtherDelegate.cpp \
COtherDTD.cpp \
$(NULL)
EXPORTS = \

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

@ -23,19 +23,23 @@ DEFINES=-D_IMPL_NS_HTMLPARS
MODULE=raptor
REQUIRES=xpcom raptor
CPPSRCS=nsDeque.cpp nsHTMLContentSink.cpp nsHTMLDelegate.cpp nsHTMLDTD.cpp \
CPPSRCS=nsHTMLContentSink.cpp nsHTMLDelegate.cpp nsHTMLDTD.cpp \
nsHTMLParser.cpp nsHTMLTokens.cpp nsParserNode.cpp nsScanner.cpp \
nsToken.cpp nsTokenizer.cpp nsDefaultTokenHandler.cpp
nsToken.cpp nsTokenizer.cpp nsTokenHandler.cpp \
CNavDTD.cpp CNavDelegate.cpp \
COtherDTD.cpp COtherDelegate.cpp
EXPORTS=nshtmlpars.h nsIContentSink.h nsIHTMLContentSink.h \
nsHTMLTokens.h nsIParserNode.h nsIParser.h nsToken.h
CPP_OBJS=.\$(OBJDIR)\nsDeque.obj .\$(OBJDIR)\nsHTMLContentSink.obj \
.\$(OBJDIR)\nsHTMLDelegate.obj .\$(OBJDIR)\nsHTMLParser.obj \
CPP_OBJS=.\$(OBJDIR)\nsHTMLContentSink.obj \
.\$(OBJDIR)\nsHTMLDelegate.obj .\$(OBJDIR)\nsHTMLParser.obj \
.\$(OBJDIR)\nsHTMLDTD.obj \
.\$(OBJDIR)\nsHTMLTokens.obj .\$(OBJDIR)\nsParserNode.obj \
.\$(OBJDIR)\nsScanner.obj .\$(OBJDIR)\nsToken.obj \
.\$(OBJDIR)\nsTokenizer.obj .\$(OBJDIR)\nsDefaultTokenHandler.obj
.\$(OBJDIR)\CNavDelegate.obj .\$(OBJDIR)\CNavDTD.obj \
.\$(OBJDIR)\COtherDelegate.obj .\$(OBJDIR)\COtherDTD.obj \
.\$(OBJDIR)\nsHTMLTokens.obj .\$(OBJDIR)\nsParserNode.obj \
.\$(OBJDIR)\nsScanner.obj .\$(OBJDIR)\nsToken.obj \
.\$(OBJDIR)\nsTokenizer.obj .\$(OBJDIR)\nsTokenHandler.obj
LINCS=-I$(XPDIST)\public\xpcom -I$(XPDIST)\public\raptor

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

@ -520,7 +520,7 @@ PRBool nsHTMLDTD::CanContainIndirect(PRInt32 aParent,PRInt32 aChild) const {
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
PRBool nsHTMLDTD::CanDisregard(PRInt32 aParent,PRInt32 aChild) const {
PRBool nsHTMLDTD::CanOmit(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=PR_FALSE;
switch((eHTMLTags)aParent) {
@ -671,4 +671,19 @@ PRBool nsHTMLDTD::VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const {
return result;
}
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
PRInt32 nsHTMLDTD::CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const {
PRInt32 result=0;
return result;
}

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

@ -92,7 +92,7 @@ class nsHTMLDTD : public nsIDTD {
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool CanDisregard(PRInt32 aParent,PRInt32 aChild)const;
virtual PRBool CanOmit(PRInt32 aParent,PRInt32 aChild)const;
/** -------------------------------------------------------
* This method gets called to determine whether a given
@ -127,6 +127,19 @@ class nsHTMLDTD : public nsIDTD {
*/ //-----------------------------------------------------
virtual PRBool VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const;
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
virtual PRInt32 CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const;
};

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

@ -43,6 +43,28 @@ CHTMLTokenizerDelegate::CHTMLTokenizerDelegate() :
ITokenizerDelegate(), mTokenDeque() {
}
/**-------------------------------------------------------
* Default constructor
*
* @updated gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
CHTMLTokenizerDelegate::CHTMLTokenizerDelegate(CHTMLTokenizerDelegate& aDelegate) :
ITokenizerDelegate(), mTokenDeque() {
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
eParseMode CHTMLTokenizerDelegate::GetParseMode() const {
return eParseMode_unknown;
}
/**-------------------------------------------------------
* This method is called just after a "<" has been consumed
* and we know we're at the start of some kind of tagged
@ -75,10 +97,10 @@ CToken* CHTMLTokenizerDelegate::ConsumeTag(PRUnichar aChar,CScanner& aScanner,PR
nsAutoString temp("<");
return ConsumeText(temp,aScanner,anErrorCode);
}
}
} //switch
if(result!=0) {
anErrorCode= result->Consume(aChar,&aScanner); //tell new token to finish consuming text...
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(anErrorCode) {
result=0;
delete result;
@ -103,7 +125,7 @@ void CHTMLTokenizerDelegate::ConsumeAttributes(PRUnichar aChar,CScanner& aScanne
while((!done) && (anErrorCode==kNoError)) {
CToken* result = new CAttributeToken(as);
if(result){
anErrorCode= result->Consume(aChar,&aScanner); //tell new token to finish consuming text...
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
mTokenDeque.Push(result);
}
aScanner.Peek(aChar);
@ -133,7 +155,7 @@ CToken* CHTMLTokenizerDelegate::ConsumeContentToEndTag(const nsString& aString,P
endTag.Append(aString);
endTag.Append(">");
CSkippedContentToken* sc=new CSkippedContentToken(endTag);
anErrorCode= sc->Consume(aChar,&aScanner); //tell new token to finish consuming text...
anErrorCode= sc->Consume(aChar,aScanner); //tell new token to finish consuming text...
return sc;
}
@ -150,10 +172,10 @@ CToken* CHTMLTokenizerDelegate::ConsumeContentToEndTag(const nsString& aString,P
CToken* CHTMLTokenizerDelegate::ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CStartToken* result=new CStartToken(nsAutoString(""));
if(result) {
anErrorCode= result->Consume(aChar,&aScanner); //tell new token to finish consuming text...
if(result->IsAttributed())
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(result->IsAttributed()) {
ConsumeAttributes(aChar,aScanner,anErrorCode);
}
//now that that's over with, we have one more problem to solve.
//In the case that we just read a <SCRIPT> or <STYLE> tags, we should go and
//consume all the content itself.
@ -176,8 +198,8 @@ CToken* CHTMLTokenizerDelegate::ConsumeStartTag(PRUnichar aChar,CScanner& aScann
CEndToken* endtoken=new CEndToken(str);
mTokenDeque.Push(endtoken);
}
}
} //if
} //if
}
return result;
}
@ -198,14 +220,13 @@ CToken* CHTMLTokenizerDelegate::ConsumeEntity(PRUnichar aChar,CScanner& aScanner
anErrorCode=aScanner.GetChar(ch);
if(nsString::IsAlpha(ch)) { //handle common enity references &xxx; or &#000.
result = new CEntityToken(nsAutoString(""));
anErrorCode= result->Consume(ch,&aScanner); //tell new token to finish consuming text...
anErrorCode= result->Consume(ch,aScanner); //tell new token to finish consuming text...
}
else if(kHashsign==ch) {
result = new CEntityToken(nsAutoString(""));
anErrorCode=result->Consume(ch,&aScanner);
anErrorCode=result->Consume(ch,aScanner);
}
else
{
else {
//oops, we're actually looking at plain text...
nsAutoString temp("&");
return ConsumeText(temp,aScanner,anErrorCode);
@ -226,7 +247,7 @@ CToken* CHTMLTokenizerDelegate::ConsumeEntity(PRUnichar aChar,CScanner& aScanner
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::ConsumeWhitespace(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CToken* result = new CWhitespaceToken(nsAutoString(""));
anErrorCode=result->Consume(aChar,&aScanner);
anErrorCode=result->Consume(aChar,aScanner);
return result;
}
#endif
@ -243,7 +264,7 @@ CToken* CHTMLTokenizerDelegate::ConsumeWhitespace(PRUnichar aChar,CScanner& aSca
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::ConsumeComment(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode){
CToken* result= new CCommentToken(nsAutoString(""));
anErrorCode=result->Consume(aChar,&aScanner);
anErrorCode=result->Consume(aChar,aScanner);
return result;
}
@ -259,9 +280,10 @@ CToken* CHTMLTokenizerDelegate::ConsumeComment(PRUnichar aChar,CScanner& aScanne
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::ConsumeText(const nsString& aString,CScanner& aScanner,PRInt32& anErrorCode){
CToken* result=new CTextToken(aString);
PRUnichar ch;
if(result)
anErrorCode=result->Consume(ch,&aScanner);
if(result) {
PRUnichar ch;
anErrorCode=result->Consume(ch,aScanner);
}
return result;
}
@ -277,8 +299,9 @@ CToken* CHTMLTokenizerDelegate::ConsumeText(const nsString& aString,CScanner& aS
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::ConsumeNewline(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode){
CToken* result=new CNewlineToken(nsAutoString(""));
if(result)
anErrorCode=result->Consume(aChar,&aScanner);
if(result) {
anErrorCode=result->Consume(aChar,aScanner);
}
return result;
}
#endif
@ -295,44 +318,54 @@ CToken* CHTMLTokenizerDelegate::ConsumeNewline(PRUnichar aChar,CScanner& aScanne
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::GetToken(CScanner* aScanner,PRInt32& anErrorCode){
CToken* CHTMLTokenizerDelegate::GetToken(CScanner& aScanner,PRInt32& anErrorCode){
CToken* result=0;
PRUnichar aChar;
if(mTokenDeque.GetSize()>0)
return mTokenDeque.Pop();
if(mTokenDeque.GetSize()>0) {
return (CToken*)mTokenDeque.Pop();
}
while(!aScanner->Eof())
{
anErrorCode=aScanner->GetChar(aChar);
while(!aScanner.Eof()) {
anErrorCode=aScanner.GetChar(aChar);
switch(aChar) {
case kAmpersand:
return ConsumeEntity(aChar,*aScanner,anErrorCode);
return ConsumeEntity(aChar,aScanner,anErrorCode);
case kLessThan:
return ConsumeTag(aChar,*aScanner,anErrorCode);
return ConsumeTag(aChar,aScanner,anErrorCode);
#ifdef TOKENIZE_CRLF
case kCR: case kLF:
return ConsumeNewline(aChar,*aScanner,anErrorCode);
return ConsumeNewline(aChar,aScanner,anErrorCode);
case kNotFound:
break;
#endif
default:
#ifdef TOKENIZE_WHITESPACE
if(nsString::IsSpace(aChar))
return ConsumeWhitespace(aChar,*aScanner,anErrorCode);
return ConsumeWhitespace(aChar,aScanner,anErrorCode);
else
#endif
{
nsAutoString temp(aChar);
return ConsumeText(temp,*aScanner,anErrorCode);
return ConsumeText(temp,aScanner,anErrorCode);
}
}
} //switch
if(anErrorCode==kEOF)
anErrorCode=0;
}
} //while
return result;
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::CreateTokenOfType(eHTMLTokenTypes aType) {
return 0;
}
/**-------------------------------------------------------
* This method is by the tokenizer, once for each new token
* we've constructed. This method determines whether or not

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

@ -43,40 +43,42 @@
#include "nsITokenizerDelegate.h"
#include "nsDeque.h"
#define MAXCOMMANDLEN (18)
class CHTMLTokenizerDelegate : public ITokenizerDelegate {
public:
CHTMLTokenizerDelegate();
CHTMLTokenizerDelegate();
CHTMLTokenizerDelegate(CHTMLTokenizerDelegate& aDelegate);
virtual CToken* GetToken(CScanner* aScanner,PRInt32& anErrorCode);
virtual PRBool WillAddToken(CToken& aToken);
virtual CToken* GetToken(CScanner& aScanner,PRInt32& anErrorCode);
virtual PRBool WillAddToken(CToken& aToken);
virtual PRBool WillTokenize();
virtual PRBool DidTokenize();
static void SelfTest();
virtual PRBool WillTokenize();
virtual PRBool DidTokenize();
virtual eParseMode GetParseMode() const;
static void SelfTest();
protected:
CToken* ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
void ConsumeAttributes(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeText(const nsString& aString,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* CreateTokenOfType(eHTMLTokenTypes aType);
CToken* ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
void ConsumeAttributes(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeText(const nsString& aString,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
#ifdef TOKENIZE_WHITESPACE
CToken* ConsumeWhitespace(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeWhitespace(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
#endif
CToken* ConsumeComment(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeComment(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
#ifdef TOKENIZE_CRLF
CToken* ConsumeNewline(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeNewline(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
#endif
//the only special case method...
CToken* ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CDeque mTokenDeque;
nsDeque mTokenDeque;
};

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

@ -17,21 +17,26 @@
*/
#include "nsHTMLParser.h"
#include "nsHTMLDelegate.h"
#include "nsHTMLContentSink.h"
#include "nsHTMLContentSink.h"
#include "nsTokenizer.h"
#include "nsHTMLTokens.h"
#include "nsString.h"
#include "nsIURL.h"
#include "nsDefaultTokenHandler.h"
#include "nsCRT.h"
#include "nsHTMLDTD.h"
#include "COtherDelegate.h"
#include "COtherDTD.h"
#include "CNavDelegate.h"
#include "CNavDTD.h"
static NS_DEFINE_IID(kISupportsIID, NS_ISUPPORTS_IID);
static NS_DEFINE_IID(kClassIID, NS_IHTML_PARSER_IID);
static NS_DEFINE_IID(kIParserIID, NS_IPARSER_IID);
static NS_DEFINE_IID(kIHTMLContentSinkIID, NS_IHTMLCONTENTSINK_IID);
static const char* kNullURL = "Error: Null URL given";
static const char* kNullTokenizer = "Error: Unable to construct tokenizer";
static const char* kNullToken = "Error: Null token given";
static const char* kInvalidTagStackPos = "Error: invalid tag stack position";
/**-------------------------------------------------------
@ -84,12 +89,13 @@ void nsHTMLParser::InitializeDefaultTokenHandlers() {
nsHTMLParser::nsHTMLParser() {
NS_INIT_REFCNT();
mSink=0;
mTokenHandlerCount=0;
mTagStackPos=0;
mContextStackPos=0;
mCurrentPos=0;
nsCRT::zero(mTagStack,sizeof(mTagStack));
mParseMode=eParseMode_unknown;
nsCRT::zero(mContextStack,sizeof(mContextStack));
nsCRT::zero(mTokenHandlers,sizeof(mTokenHandlers));
mDTD=new nsHTMLDTD();
mDTD=0;
mTokenHandlerCount=0;
InitializeDefaultTokenHandlers();
}
@ -102,13 +108,16 @@ nsHTMLParser::nsHTMLParser() {
* @return
*------------------------------------------------------*/
nsHTMLParser::~nsHTMLParser() {
DeleteTokenHandlers();
if(mCurrentPos)
delete mCurrentPos;
mCurrentPos=0;
if(mTokenizer)
delete mTokenizer;
if(mDTD)
delete mDTD;
mTokenizer=0;
mDTD=0;
NS_IF_RELEASE(mSink);
}
@ -160,8 +169,8 @@ nsresult nsHTMLParser::QueryInterface(const nsIID& aIID, void** aInstancePtr)
*------------------------------------------------------*/
eHTMLTags nsHTMLParser::NodeAt(PRInt32 aPos) const {
NS_PRECONDITION(0 <= aPos, "bad nodeAt");
if((aPos>-1) && (aPos<mTagStackPos))
return mTagStack[aPos];
if((aPos>-1) && (aPos<mContextStackPos))
return mContextStack[aPos];
return (eHTMLTags)kNotFound;
}
@ -174,8 +183,8 @@ eHTMLTags nsHTMLParser::NodeAt(PRInt32 aPos) const {
* @return
*------------------------------------------------------*/
eHTMLTags nsHTMLParser::GetTopNode() const {
if(mTagStackPos)
return mTagStack[mTagStackPos-1];
if(mContextStackPos)
return mContextStack[mContextStackPos-1];
return (eHTMLTags)kNotFound;
}
@ -188,8 +197,8 @@ eHTMLTags nsHTMLParser::GetTopNode() const {
* @return topmost index of tag on stack
*------------------------------------------------------*/
PRInt32 nsHTMLParser::GetTopmostIndex(eHTMLTags aTag) const {
for(int i=mTagStackPos-1;i>=0;i--){
if(mTagStack[i]==aTag)
for(int i=mContextStackPos-1;i>=0;i--){
if(mContextStack[i]==aTag)
return i;
}
return kNotFound;
@ -216,10 +225,9 @@ PRBool nsHTMLParser::IsOpen(eHTMLTags aTag) const {
* @return
*------------------------------------------------------*/
PRInt32 nsHTMLParser::GetStackPos() const {
return mTagStackPos;
return mContextStackPos;
}
/**-------------------------------------------------------
* Finds a tag handler for the given tag type, given in string.
*
@ -227,7 +235,22 @@ PRInt32 nsHTMLParser::GetStackPos() const {
* @param aString contains name of tag to be handled
* @return valid tag handler (if found) or null
*------------------------------------------------------*/
CDefaultTokenHandler* nsHTMLParser::GetTokenHandler(const nsString& aString) const{
nsHTMLParser& nsHTMLParser::DeleteTokenHandlers(void) {
for(int i=0;i<mTokenHandlerCount;i++){
delete mTokenHandlers[i];
}
mTokenHandlerCount=0;
return *this;
}
/**-------------------------------------------------------
* Finds a tag handler for the given tag type, given in string.
*
* @update gess 4/2/98
* @param aString contains name of tag to be handled
* @return valid tag handler (if found) or null
*------------------------------------------------------*/
CTokenHandler* nsHTMLParser::GetTokenHandler(const nsString& aString) const{
eHTMLTokenTypes theType=DetermineTokenType(aString);
return GetTokenHandler(theType);
}
@ -240,7 +263,7 @@ CDefaultTokenHandler* nsHTMLParser::GetTokenHandler(const nsString& aString) con
* @param aTagType type of tag to be handled
* @return valid tag handler (if found) or null
*------------------------------------------------------*/
CDefaultTokenHandler* nsHTMLParser::GetTokenHandler(eHTMLTokenTypes aType) const {
CTokenHandler* nsHTMLParser::GetTokenHandler(eHTMLTokenTypes aType) const {
for(int i=0;i<mTokenHandlerCount;i++) {
if(mTokenHandlers[i]->CanHandle(aType)) {
return mTokenHandlers[i];
@ -257,9 +280,14 @@ CDefaultTokenHandler* nsHTMLParser::GetTokenHandler(eHTMLTokenTypes aType) const
* @param
* @return
*------------------------------------------------------*/
CDefaultTokenHandler* nsHTMLParser::AddTokenHandler(CDefaultTokenHandler* aHandler) {
CTokenHandler* nsHTMLParser::AddTokenHandler(CTokenHandler* aHandler) {
NS_ASSERTION(0!=aHandler,"Error: Null handler argument");
if(aHandler) {
int max=sizeof(mTokenHandlers)/sizeof(mTokenHandlers[0]);
if(mTokenHandlerCount<max) {
mTokenHandlers[mTokenHandlerCount++]=aHandler;
}
}
return 0;
}
@ -272,20 +300,79 @@ CDefaultTokenHandler* nsHTMLParser::AddTokenHandler(CDefaultTokenHandler* aHandl
* @param nsIContentSink interface for node receiver
* @return
*------------------------------------------------------*/
void nsHTMLParser::SetContentSink(nsIContentSink* aSink) {
nsIContentSink* nsHTMLParser::SetContentSink(nsIContentSink* aSink) {
NS_PRECONDITION(0!=aSink,"sink cannot be null!");
nsIContentSink* old=mSink;
if(aSink) {
nsIHTMLContentSink* htmlSink;
if (NS_OK == aSink->QueryInterface(kIHTMLContentSinkIID, (void**)&htmlSink)) {
if ((nsHTMLContentSink*)(htmlSink) != mSink) {
NS_IF_RELEASE(mSink);
mSink = (nsHTMLContentSink*)(htmlSink);
}
else {
NS_RELEASE(htmlSink);
}
}
mSink=(nsHTMLContentSink*)(aSink);
}
return old;
}
/**-------------------------------------------------------
* This is where we loop over the tokens created in the
* tokenization phase, and try to make sense out of them.
*
* @update gess 3/25/98
* @param
* @return PR_TRUE if parse succeeded, PR_FALSE otherwise.
*------------------------------------------------------*/
PRBool nsHTMLParser::IterateTokens() {
nsDeque& deque=mTokenizer->GetDeque();
nsDequeIterator e=deque.End();
if(mCurrentPos)
delete mCurrentPos; //don't leak, now!
mCurrentPos=new nsDequeIterator(deque.Begin());
CToken* theToken;
PRBool done=PR_FALSE;
PRBool result=PR_TRUE;
PRInt32 iteration=0;
while((!done) && (result)) {
theToken=(CToken*)mCurrentPos->GetCurrent();
eHTMLTokenTypes type=eHTMLTokenTypes(theToken->GetTokenType());
iteration++; //debug purposes...
switch(eHTMLTokenTypes(type)){
case eToken_start:
result=HandleStartToken(theToken); break;
case eToken_end:
result=HandleEndToken(theToken); break;
case eToken_entity:
result=HandleEntityToken(theToken); break;
case eToken_text:
result=HandleTextToken(theToken); break;
case eToken_newline:
result=HandleNewlineToken(theToken); break;
case eToken_skippedcontent:
//used in cases like <SCRIPT> where we skip over script content.
result=HandleSkippedContentToken(theToken); break;
case eToken_attribute:
result=HandleAttributeToken(theToken); break;
case eToken_script:
result=HandleScriptToken(theToken); break;
case eToken_style:
result=HandleStyleToken(theToken); break;
case eToken_comment:
result=HandleCommentToken(theToken); break;
case eToken_whitespace:
result=HandleWhitespaceToken(theToken); break;
default:
//for all these non-interesting types, just skip them for now.
//later you have to Handle them, because they're relevent to certain containers (eg PRE).
break;
}
mDTD->VerifyContextStack(mContextStack,mContextStackPos);
++(*mCurrentPos);
done=PRBool(e==*mCurrentPos);
}
//One last thing...close any open containers.
if((PR_TRUE==result) && (mContextStackPos>0)) {
result=CloseContainersTo(0);
}
return result;
}
/**-------------------------------------------------------
@ -300,73 +387,53 @@ void nsHTMLParser::SetContentSink(nsIContentSink* aSink) {
* @return PR_TRUE if parse succeeded, PR_FALSE otherwise.
*------------------------------------------------------*/
PRBool nsHTMLParser::Parse(nsIURL* aURL){
NS_PRECONDITION(0!=aURL,"Error: URL cannot be null!");
return Parse(aURL,eParseMode_navigator);
}
/**-------------------------------------------------------
* This is the main controlling routine in the parsing process.
* Note that it may get called multiple times for the same scanner,
* since this is a pushed based system, and all the tokens may
* not have been consumed by the scanner during a given invocation
* of this method.
*
* @update gess 3/25/98
* @param aFilename -- const char* containing file to be parsed.
* @return PR_TRUE if parse succeeded, PR_FALSE otherwise.
*------------------------------------------------------*/
PRBool nsHTMLParser::Parse(nsIURL* aURL,eParseMode aMode){
NS_PRECONDITION(0!=aURL,kNullURL);
PRBool result=PR_FALSE;
if(aURL) {
result=PR_TRUE;
CHTMLTokenizerDelegate delegate;
mTokenizer=new CTokenizer(aURL, delegate);
mParseMode=aMode;
ITokenizerDelegate* theDelegate=0;
switch(mParseMode) {
case eParseMode_navigator:
theDelegate=new CNavDelegate();
mDTD= new CNavDTD();
break;
case eParseMode_other:
theDelegate=new COtherDelegate();
mDTD= new COtherDTD();
break;
default:
break;
}
if(!theDelegate) {
NS_ERROR(kNullTokenizer);
return PR_FALSE;
}
if(!mDTD) {
mDTD= new nsHTMLDTD();
}
mTokenizer=new CTokenizer(aURL, theDelegate, mParseMode);
mTokenizer->Tokenize();
//#define VERBOSE_DEBUG
#ifdef VERBOSE_DEBUG
mTokenizer->DebugDumpTokens(cout);
#endif
CDeque& deque=mTokenizer->GetDeque();
CDequeIterator e=deque.End();
if(mCurrentPos)
delete mCurrentPos; //don't leak, now!
mCurrentPos=new CDequeIterator(deque.Begin());
CToken* theToken;
PRBool done=PR_FALSE;
PRInt32 iteration=0;
while((!done) && (result)) {
theToken=*mCurrentPos;
eHTMLTokenTypes type=eHTMLTokenTypes(theToken->GetTokenType());
iteration++; //debug purposes...
switch(eHTMLTokenTypes(type)){
case eToken_start:
result=HandleStartToken(theToken); break;
case eToken_end:
result=HandleEndToken(theToken); break;
case eToken_entity:
result=HandleEntityToken(theToken); break;
case eToken_text:
result=HandleTextToken(theToken); break;
case eToken_newline:
result=HandleNewlineToken(theToken); break;
case eToken_skippedcontent:
//used in cases like <SCRIPT> where we skip over script content.
result=HandleSkippedContentToken(theToken); break;
case eToken_attribute:
result=HandleAttributeToken(theToken); break;
case eToken_script:
result=HandleScriptToken(theToken); break;
case eToken_style:
result=HandleStyleToken(theToken); break;
case eToken_comment:
result=HandleCommentToken(theToken); break;
case eToken_whitespace:
result=HandleWhitespaceToken(theToken); break;
default:
//for all these non-interesting types, just skip them for now.
//later you have to Handle them, because they're relevent to certain containers (eg PRE).
break;
}
mDTD->VerifyContextStack(mTagStack,mTagStackPos);
done=PRBool(++(*mCurrentPos)==e);
}
//One last thing...close any open containers.
if((PR_TRUE==result) && (mTagStackPos>0)) {
result=CloseContainersTo(0);
}
result=IterateTokens();
}
return result;
}
@ -383,7 +450,7 @@ PRBool nsHTMLParser::Parse(nsIURL* aURL){
* @return PR_TRUE if parsing concluded successfully.
*------------------------------------------------------*/
PRBool nsHTMLParser::ResumeParse() {
PRBool result=PR_TRUE;
PRBool result=IterateTokens();
return result;
}
@ -396,8 +463,8 @@ PRBool nsHTMLParser::ResumeParse() {
*------------------------------------------------------*/
PRInt32 nsHTMLParser::CollectAttributes(nsCParserNode& aNode){
eHTMLTokenTypes subtype=eToken_attribute;
CDeque& deque=mTokenizer->GetDeque();
CDequeIterator end=deque.End();
nsDeque& deque=mTokenizer->GetDeque();
nsDequeIterator end=deque.End();
while((*mCurrentPos!=end) && (eToken_attribute==subtype)) {
CHTMLToken* tkn=(CHTMLToken*)(++(*mCurrentPos));
@ -418,8 +485,8 @@ PRInt32 nsHTMLParser::CollectAttributes(nsCParserNode& aNode){
*------------------------------------------------------*/
PRInt32 nsHTMLParser::CollectSkippedContent(nsCParserNode& aNode){
eHTMLTokenTypes subtype=eToken_attribute;
CDeque& deque=mTokenizer->GetDeque();
CDequeIterator end=deque.End();
nsDeque& deque=mTokenizer->GetDeque();
nsDequeIterator end=deque.End();
PRInt32 count=0;
while((*mCurrentPos!=end) && (eToken_attribute==subtype)) {
@ -450,7 +517,7 @@ PRInt32 nsHTMLParser::CollectSkippedContent(nsCParserNode& aNode){
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleStartToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_FALSE;
CStartToken* st= (CStartToken*)(aToken);
@ -551,7 +618,7 @@ PRBool nsHTMLParser::HandleStartToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleEndToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_FALSE;
CEndToken* st = (CEndToken*)(aToken);
@ -605,7 +672,7 @@ PRBool nsHTMLParser::HandleEndToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleEntityToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
CEntityToken* et = (CEntityToken*)(aToken);
PRBool result=PR_TRUE;
nsCParserNode aNode((CHTMLToken*)aToken);
@ -624,6 +691,7 @@ PRBool nsHTMLParser::HandleEntityToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleCommentToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,kNullToken);
return PR_TRUE;
}
@ -638,11 +706,13 @@ PRBool nsHTMLParser::HandleCommentToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleWhitespaceToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_TRUE;
if(PR_TRUE==IsWithinBody()) {
//now we know we're in the body <i>somewhere</i>.
//let's see if the current tag can contain a ws.
result=mDTD->CanDisregard(mTagStack[mTagStackPos-1],eHTMLTag_whitespace);
result=mDTD->CanOmit(mContextStack[mContextStackPos-1],eHTMLTag_whitespace);
if(PR_FALSE==result)
result=HandleTextToken(aToken);
}
@ -660,11 +730,13 @@ PRBool nsHTMLParser::HandleWhitespaceToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleNewlineToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_TRUE;
if(PR_TRUE==IsWithinBody()) {
//now we know we're in the body <i>somewhere</i>.
//let's see if the current tag can contain a ws.
result=mDTD->CanDisregard(mTagStack[mTagStackPos-1],eHTMLTag_newline);
result=mDTD->CanOmit(mContextStack[mContextStackPos-1],eHTMLTag_newline);
if(PR_FALSE==result)
result=HandleTextToken(aToken);
}
@ -682,7 +754,8 @@ PRBool nsHTMLParser::HandleNewlineToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleTextToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_TRUE;
nsCParserNode aNode((CHTMLToken*)aToken);
result=AddLeaf(aNode);
@ -700,7 +773,8 @@ PRBool nsHTMLParser::HandleTextToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleSkippedContentToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_TRUE;
if(IsWithinBody()) {
@ -721,7 +795,7 @@ PRBool nsHTMLParser::HandleSkippedContentToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleAttributeToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
NS_ERROR("attribute encountered -- this shouldn't happen!");
CAttributeToken* at = (CAttributeToken*)(aToken);
@ -738,7 +812,7 @@ PRBool nsHTMLParser::HandleAttributeToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleScriptToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
CScriptToken* st = (CScriptToken*)(aToken);
PRBool result=PR_TRUE;
@ -754,7 +828,7 @@ PRBool nsHTMLParser::HandleScriptToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleStyleToken(CToken* aToken){
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
CStyleToken* st = (CStyleToken*)(aToken);
PRBool result=PR_TRUE;
@ -770,8 +844,8 @@ PRBool nsHTMLParser::HandleStyleToken(CToken* aToken){
* @return PR_TRUE if given tag can contain other tags
*------------------------------------------------------*/
PRBool nsHTMLParser::IsWithinBody(void) const {
for(int i=0;i<mTagStackPos;i++) {
if(eHTMLTag_body==mTagStack[i])
for(int i=0;i<mContextStackPos;i++) {
if(eHTMLTag_body==mContextStack[i])
return PR_TRUE;
}
return PR_FALSE;
@ -787,9 +861,10 @@ PRBool nsHTMLParser::IsWithinBody(void) const {
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenHTML(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=mSink->OpenHTML(aNode);
mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
mContextStack[mContextStackPos++]=(eHTMLTags)aNode.GetNodeType();
return result;
}
@ -803,9 +878,9 @@ PRBool nsHTMLParser::OpenHTML(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseHTML(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRBool result=mSink->CloseHTML(aNode);
mTagStack[--mTagStackPos]=eHTMLTag_unknown;
mContextStack[--mContextStackPos]=eHTMLTag_unknown;
return result;
}
@ -819,9 +894,7 @@ PRBool nsHTMLParser::CloseHTML(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenHead(const nsIParserNode& aNode){
// NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
PRBool result=mSink->OpenHead(aNode);
// mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
return result;
}
@ -834,9 +907,7 @@ PRBool nsHTMLParser::OpenHead(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseHead(const nsIParserNode& aNode){
// NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
PRBool result=mSink->CloseHead(aNode);
// mTagStack[--mTagStackPos]=eHTMLTag_unknown;
return result;
}
@ -849,7 +920,7 @@ PRBool nsHTMLParser::CloseHead(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenBody(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=PR_TRUE;
eHTMLTags topTag=(eHTMLTags)nsHTMLParser::GetTopNode();
@ -882,7 +953,7 @@ PRBool nsHTMLParser::OpenBody(const nsIParserNode& aNode){
if(PR_TRUE==result) {
result=mSink->OpenBody(aNode);
mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
mContextStack[mContextStackPos++]=(eHTMLTags)aNode.GetNodeType();
}
return result;
}
@ -896,9 +967,9 @@ PRBool nsHTMLParser::OpenBody(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseBody(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=mSink->CloseBody(aNode);
mTagStack[--mTagStackPos]=eHTMLTag_unknown;
mContextStack[--mContextStackPos]=eHTMLTag_unknown;
return result;
}
@ -911,9 +982,9 @@ PRBool nsHTMLParser::CloseBody(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenForm(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=mSink->OpenForm(aNode);
mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
mContextStack[mContextStackPos++]=(eHTMLTags)aNode.GetNodeType();
return result;
}
@ -926,9 +997,9 @@ PRBool nsHTMLParser::OpenForm(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseForm(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRBool result=mSink->CloseContainer(aNode);
mTagStack[--mTagStackPos]=eHTMLTag_unknown;
mContextStack[--mContextStackPos]=eHTMLTag_unknown;
return result;
}
@ -941,9 +1012,9 @@ PRBool nsHTMLParser::CloseForm(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenFrameset(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=mSink->OpenFrameset(aNode);
mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
mContextStack[mContextStackPos++]=(eHTMLTags)aNode.GetNodeType();
return result;
}
@ -956,9 +1027,9 @@ PRBool nsHTMLParser::OpenFrameset(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseFrameset(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRBool result=mSink->CloseFrameset(aNode);
mTagStack[--mTagStackPos]=eHTMLTag_unknown;
mContextStack[--mContextStackPos]=eHTMLTag_unknown;
return result;
}
@ -971,9 +1042,9 @@ PRBool nsHTMLParser::CloseFrameset(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenContainer(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=mSink->OpenContainer(aNode);
mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
mContextStack[mContextStackPos++]=(eHTMLTags)aNode.GetNodeType();
return result;
}
@ -986,7 +1057,7 @@ PRBool nsHTMLParser::OpenContainer(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseContainer(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRBool result=PR_FALSE;
//XXX Hack! We know this is wrong, but it works
@ -1010,7 +1081,7 @@ PRBool nsHTMLParser::CloseContainer(const nsIParserNode& aNode){
case eHTMLTag_title:
default:
result=mSink->CloseContainer(aNode);
mTagStack[--mTagStackPos]=eHTMLTag_unknown;
mContextStack[--mContextStackPos]=eHTMLTag_unknown;
break;
}
return result;
@ -1025,16 +1096,16 @@ PRBool nsHTMLParser::CloseContainer(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseContainersTo(PRInt32 anIndex){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRBool result=PR_TRUE;
nsAutoString empty;
CHTMLToken aToken(empty);
nsCParserNode theNode(&aToken);
if((anIndex<mTagStackPos) && (anIndex>=0)) {
while(mTagStackPos>anIndex) {
aToken.SetHTMLTag(mTagStack[mTagStackPos-1]);
if((anIndex<mContextStackPos) && (anIndex>=0)) {
while(mContextStackPos>anIndex) {
aToken.SetHTMLTag(mContextStack[mContextStackPos-1]);
result=CloseContainer(theNode);
}
}
@ -1050,7 +1121,7 @@ PRBool nsHTMLParser::CloseContainersTo(PRInt32 anIndex){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseContainersTo(eHTMLTags aTag){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRInt32 pos=GetTopmostIndex(aTag);
PRBool result=PR_FALSE;
@ -1082,11 +1153,11 @@ PRBool nsHTMLParser::CloseContainersTo(eHTMLTags aTag){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseTopmostContainer(){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
nsAutoString empty;
CEndToken aToken(empty);
aToken.SetHTMLTag(mTagStack[mTagStackPos-1]);
aToken.SetHTMLTag(mContextStack[mContextStackPos-1]);
nsCParserNode theNode(&aToken);
return CloseContainer(theNode);
@ -1132,8 +1203,8 @@ PRBool nsHTMLParser::CreateContextStackFor(PRInt32 aChildTag){
//now, compare requested stack against existing stack...
PRInt32 pos=0;
while(pos<mTagStackPos) {
if(mTagStack[pos]==tags[tagCount-1-pos]) {
while(pos<mContextStackPos) {
if(mContextStack[pos]==tags[tagCount-1-pos]) {
pos++;
}
else {

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

@ -59,7 +59,8 @@
#include "nsDeque.h"
#include "nsHTMLTokens.h"
#include "nsParserNode.h"
#include "nsDefaultTokenHandler.h"
#include "nsTokenHandler.h"
#include "nsParserTypes.h"
#define NS_IHTML_PARSER_IID \
@ -77,13 +78,14 @@ class nsHTMLDTD;
class nsHTMLParser : public nsIParser {
public:
friend class CDefaultTokenHandler;
friend class CTokenHandler;
NS_DECL_ISUPPORTS
nsHTMLParser();
~nsHTMLParser();
virtual void SetContentSink(nsIContentSink* aSink);
virtual nsIContentSink* SetContentSink(nsIContentSink* aSink);
virtual PRBool Parse(nsIURL* aURL);
virtual PRBool Parse(nsIURL* aURL,eParseMode aMode);
virtual PRBool ResumeParse();
@ -102,6 +104,7 @@ friend class CDefaultTokenHandler;
PRBool IsWithinBody(void) const;
protected:
PRBool IterateTokens();
eHTMLTags NodeAt(PRInt32 aPos) const;
eHTMLTags GetTopNode() const;
PRInt32 GetStackPos() const;
@ -109,9 +112,10 @@ friend class CDefaultTokenHandler;
PRInt32 CollectAttributes(nsCParserNode& aNode);
PRInt32 CollectSkippedContent(nsCParserNode& aNode);
void InitializeDefaultTokenHandlers();
CDefaultTokenHandler* GetTokenHandler(const nsString& aString) const;
CDefaultTokenHandler* GetTokenHandler(eHTMLTokenTypes aType) const;
CDefaultTokenHandler* AddTokenHandler(CDefaultTokenHandler* aHandler);
CTokenHandler* GetTokenHandler(const nsString& aString) const;
CTokenHandler* GetTokenHandler(eHTMLTokenTypes aType) const;
CTokenHandler* AddTokenHandler(CTokenHandler* aHandler);
nsHTMLParser& DeleteTokenHandlers(void);
protected:
@ -142,14 +146,15 @@ friend class CDefaultTokenHandler;
nsIHTMLContentSink* mSink;
CTokenizer* mTokenizer;
eHTMLTags mTagStack[50];
PRInt32 mTagStackPos;
eHTMLTags mContextStack[50];
PRInt32 mContextStackPos;
CDefaultTokenHandler* mTokenHandlers[100];
PRInt32 mTokenHandlerCount;
CDequeIterator* mCurrentPos;
CTokenHandler* mTokenHandlers[100];
PRInt32 mTokenHandlerCount;
nsDequeIterator* mCurrentPos;
nsHTMLDTD* mDTD;
eParseMode mParseMode;
};

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

@ -355,27 +355,25 @@ PRBool CStartToken::IsAttributed(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CStartToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CStartToken::Consume(PRUnichar aChar, CScanner& aScanner) {
//if you're here, we've already Consumed the < char, and are
//ready to Consume the rest of the open tag identifier.
//Stop consuming as soon as you see a space or a '>'.
//NOTE: We don't Consume the tag attributes here, nor do we eat the ">"
PRInt32 result=kNoError;
mTextValue=aChar;
result=aScanner->ReadWhile(mTextValue,gIdentChars,PR_FALSE);
PRInt32 result=aScanner.ReadWhile(mTextValue,gIdentChars,PR_FALSE);
//Good. Now, let's skip whitespace after the identifier,
//and see if the next char is ">". If so, we have a complete
//tag without attributes.
aScanner->SkipWhite();
result=aScanner->GetChar(aChar);
aScanner.SkipWhite();
result=aScanner.GetChar(aChar);
if(kGreaterThan!=aChar) { //look for '>'
//push that char back, since we apparently have attributes...
aScanner->PutBack(aChar);
aScanner.PutBack(aChar);
mAttributed=PR_TRUE;
}
return result;
@ -417,21 +415,17 @@ CEndToken::CEndToken(const nsString& aName) : CHTMLToken(aName) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CEndToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CEndToken::Consume(PRUnichar aChar, CScanner& aScanner) {
//if you're here, we've already Consumed the <! chars, and are
//ready to Consume the rest of the open tag identifier.
//Stop consuming as soon as you see a space or a '>'.
//NOTE: We don't Consume the tag attributes here, nor do we eat the ">"
PRInt32 result=kNotFound;
if(aScanner) {
mTextValue="";
static nsAutoString terminals(">");
result=aScanner->ReadUntil(mTextValue,terminals,PR_FALSE);
aScanner->GetChar(aChar); //eat the closing '>;
}
mTextValue="";
static nsAutoString terminals(">");
PRInt32 result=aScanner.ReadUntil(mTextValue,terminals,PR_FALSE);
aScanner.GetChar(aChar); //eat the closing '>;
return result;
};
@ -528,21 +522,17 @@ PRInt32 CTextToken::GetTokenType(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CTextToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CTextToken::Consume(PRUnichar aChar, CScanner& aScanner) {
PRInt32 result=kNotFound;
if(aScanner) {
#ifdef TOKENIZE_CRLF
static nsAutoString terminals("&<\r\n");
#else
static nsAutoString terminals("&<");
#endif
result=aScanner->ReadUntil(mTextValue,terminals,PR_FALSE);
PRInt32 result=aScanner.ReadUntil(mTextValue,terminals,PR_FALSE);
#ifndef TOKENIZE_CRLF
mTextValue.StripChars("\r");
#endif
}
return result;
};
@ -567,37 +557,31 @@ CCommentToken::CCommentToken(const nsString& aName) : CHTMLToken(aName) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CCommentToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CCommentToken::Consume(PRUnichar aChar, CScanner& aScanner) {
PRInt32 result=kNotFound;
PRUnichar ch,ch2;
static nsAutoString terminals(">");
if(aScanner) {
aScanner->GetChar(ch);
result=aScanner->GetChar(ch);
mTextValue="<!";
if(kMinus==ch) {
aScanner->GetChar(ch2);
if(kMinus==ch2) {
//in this case, we're reading a long-form comment <-- xxx -->
mTextValue+="--";
PRInt32 findpos=-1;
while((findpos==kNotFound) && (!result)) {
result=aScanner->ReadUntil(mTextValue,terminals,PR_TRUE);
findpos=mTextValue.RFind("-->");
}
return result;
aScanner.GetChar(ch);
PRInt32 result=aScanner.GetChar(ch);
mTextValue="<!";
if(kMinus==ch) {
aScanner.GetChar(ch2);
if(kMinus==ch2) {
//in this case, we're reading a long-form comment <-- xxx -->
mTextValue+="--";
PRInt32 findpos=-1;
while((findpos==kNotFound) && (!result)) {
result=aScanner.ReadUntil(mTextValue,terminals,PR_TRUE);
findpos=mTextValue.RFind("-->");
}
return result;
}
//if you're here, we're consuming a "short-form" comment
mTextValue+=ch;
result=aScanner->ReadUntil(mTextValue,terminals,PR_TRUE);
}
//if you're here, we're consuming a "short-form" comment
mTextValue+=ch;
result=aScanner.ReadUntil(mTextValue,terminals,PR_TRUE);
return result;
};
@ -665,16 +649,11 @@ PRInt32 CNewlineToken::GetTokenType(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CNewlineToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 result=kNotFound;
if(aScanner) {
mTextValue=aChar;
static nsAutoString crlfChars("\r\n");
result=aScanner->ReadWhile(mTextValue,crlfChars,PR_FALSE);
mTextValue.StripChars("\r");
}
PRInt32 CNewlineToken::Consume(PRUnichar aChar, CScanner& aScanner) {
mTextValue=aChar;
static nsAutoString crlfChars("\r\n");
PRInt32 result=aScanner.ReadWhile(mTextValue,crlfChars,PR_FALSE);
mTextValue.StripChars("\r");
return result;
};
#endif /* TOKENIZE_CRLF */
@ -739,27 +718,24 @@ void CAttributeToken::DebugDumpToken(ostream& out) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 ConsumeQuotedString(PRUnichar aChar,nsString& aString,CScanner* aScanner){
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 ConsumeQuotedString(PRUnichar aChar,nsString& aString,CScanner& aScanner){
static nsAutoString terminals1(">'");
static nsAutoString terminals2(">\"");
PRInt32 result=kNotFound;
if(aScanner) {
switch(aChar) {
case kQuote:
result=aScanner->ReadUntil(aString,terminals2,PR_TRUE);
break;
case kApostrophe:
result=aScanner->ReadUntil(aString,terminals1,PR_TRUE);
break;
default:
break;
}
PRUnichar ch=aString.Last();
if(ch!=aChar)
aString+=aChar;
switch(aChar) {
case kQuote:
result=aScanner.ReadUntil(aString,terminals2,PR_TRUE);
break;
case kApostrophe:
result=aScanner.ReadUntil(aString,terminals1,PR_TRUE);
break;
default:
break;
}
PRUnichar ch=aString.Last();
if(ch!=aChar)
aString+=aChar;
return result;
}
@ -772,14 +748,11 @@ PRInt32 ConsumeQuotedString(PRUnichar aChar,nsString& aString,CScanner* aScanner
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 ConsumeAttributeValueText(PRUnichar aChar,nsString& aString,CScanner* aScanner){
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 ConsumeAttributeValueText(PRUnichar aChar,nsString& aString,CScanner& aScanner){
PRInt32 result=kNotFound;
if(aScanner){
static nsAutoString terminals(" \t\b\r\n>");
result=aScanner->ReadUntil(aString,terminals,PR_FALSE);
}
static nsAutoString terminals(" \t\b\r\n>");
result=aScanner.ReadUntil(aString,terminals,PR_FALSE);
return result;
}
@ -792,55 +765,51 @@ PRInt32 ConsumeAttributeValueText(PRUnichar aChar,nsString& aString,CScanner* aS
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CAttributeToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CAttributeToken::Consume(PRUnichar aChar, CScanner& aScanner) {
PRInt32 result=kNotFound;
if(aScanner) {
aScanner->SkipWhite(); //skip leading whitespace
result=aScanner->Peek(aChar);
if(kEOF!=result) {
if(kQuote==aChar) { //if you're here, handle quoted key...
aScanner->GetChar(aChar); //skip the quote sign...
mTextKey=aChar;
result=ConsumeQuotedString(aChar,mTextKey,aScanner);
}
else if(kHashsign==aChar) {
aScanner->GetChar(aChar); //skip the hash sign...
mTextKey=aChar;
result=aScanner->ReadWhile(mTextKey,gDigits,PR_TRUE);
}
else {
//If you're here, handle an unquoted key.
//Don't forget to reduce entities inline!
static nsAutoString terminals(" >=\t\b\r\n\"");
result=aScanner->ReadUntil(mTextKey,terminals,PR_FALSE);
}
aScanner.SkipWhite(); //skip leading whitespace
PRInt32 result=aScanner.Peek(aChar);
if(kEOF!=result) {
if(kQuote==aChar) { //if you're here, handle quoted key...
aScanner.GetChar(aChar); //skip the quote sign...
mTextKey=aChar;
result=ConsumeQuotedString(aChar,mTextKey,aScanner);
}
else if(kHashsign==aChar) {
aScanner.GetChar(aChar); //skip the hash sign...
mTextKey=aChar;
result=aScanner.ReadWhile(mTextKey,gDigits,PR_TRUE);
}
else {
//If you're here, handle an unquoted key.
//Don't forget to reduce entities inline!
static nsAutoString terminals(" >=\t\b\r\n\"");
result=aScanner.ReadUntil(mTextKey,terminals,PR_FALSE);
}
//now it's time to Consume the (optional) value...
if(!(result=aScanner->SkipWhite())) {
if(!(result=aScanner->Peek(aChar))) {
if(kEqual==aChar){
aScanner->GetChar(aChar); //skip the equal sign...
aScanner->SkipWhite(); //now skip any intervening whitespace
aScanner->GetChar(aChar); //and grab the next char.
if((kQuote==aChar) || (kApostrophe==aChar)) {
mTextValue=aChar;
result=ConsumeQuotedString(aChar,mTextValue,aScanner);
}
else {
mTextValue=aChar; //it's an alphanum attribute...
result=ConsumeAttributeValueText(aChar,mTextValue,aScanner);
}
aScanner->SkipWhite();
//now it's time to Consume the (optional) value...
if(!(result=aScanner.SkipWhite())) {
if(!(result=aScanner.Peek(aChar))) {
if(kEqual==aChar){
aScanner.GetChar(aChar); //skip the equal sign...
aScanner.SkipWhite(); //now skip any intervening whitespace
aScanner.GetChar(aChar); //and grab the next char.
if((kQuote==aChar) || (kApostrophe==aChar)) {
mTextValue=aChar;
result=ConsumeQuotedString(aChar,mTextValue,aScanner);
}
else {
mTextValue=aChar; //it's an alphanum attribute...
result=ConsumeAttributeValueText(aChar,mTextValue,aScanner);
}
aScanner.SkipWhite();
}
}
aScanner->Peek(aChar);
mLastAttribute= PRBool((kGreaterThan==aChar) || (kEOF==result));
}
aScanner.Peek(aChar);
mLastAttribute= PRBool((kGreaterThan==aChar) || (kEOF==result));
}
return result;
};
@ -908,15 +877,11 @@ PRInt32 CWhitespaceToken::GetTokenType(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CWhitespaceToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CWhitespaceToken::Consume(PRUnichar aChar, CScanner& aScanner) {
PRInt32 result=kNotFound;
if(aScanner) {
mTextValue=aChar;
aScanner->ReadWhile(mTextValue,gWhitespace,PR_FALSE);
mTextValue.StripChars("\r");
}
mTextValue=aChar;
PRInt32 result=aScanner.ReadWhile(mTextValue,gWhitespace,PR_FALSE);
mTextValue.StripChars("\r");
return result;
};
#endif /* TOKENIZE_WHITESPACE */
@ -931,8 +896,9 @@ PRInt32 CWhitespaceToken::Consume(PRUnichar aChar, CScanner* aScanner) {
CEntityToken::CEntityToken(const nsString& aName) : CHTMLToken(aName) {
mOrdinalValue=eToken_entity;
#ifdef VERBOSE_DEBUG
if(!VerifyEntityTable())
if(!VerifyEntityTable()) {
cout<<"Entity table is invalid!" << endl;
}
#endif
}
@ -944,14 +910,10 @@ CEntityToken::CEntityToken(const nsString& aName) : CHTMLToken(aName) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CEntityToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CEntityToken::Consume(PRUnichar aChar, CScanner& aScanner) {
PRInt32 result=kNotFound;
if(aScanner) {
mTextValue=aChar;
result=ConsumeEntity(aChar,mTextValue,aScanner);
}
mTextValue=aChar;
PRInt32 result=ConsumeEntity(aChar,mTextValue,aScanner);
return result;
};
@ -987,30 +949,27 @@ PRInt32 CEntityToken::GetTokenType(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CEntityToken::ConsumeEntity(PRUnichar aChar,nsString& aString,CScanner* aScanner){
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CEntityToken::ConsumeEntity(PRUnichar aChar,nsString& aString,CScanner& aScanner){
PRInt32 result=kNotFound;
if(aScanner) {
aScanner->Peek(aChar);
if(kLeftBrace==aChar) {
//you're consuming a script entity...
static nsAutoString terminals("}>");
result=aScanner->ReadUntil(aString,terminals,PR_FALSE);
aScanner->Peek(aChar);
if(kRightBrace==aChar) {
aString+=kRightBrace; //append rightbrace, and...
aScanner->GetChar(aChar);//yank the closing right-brace
}
aScanner.Peek(aChar);
if(kLeftBrace==aChar) {
//you're consuming a script entity...
static nsAutoString terminals("}>");
result=aScanner.ReadUntil(aString,terminals,PR_FALSE);
aScanner.Peek(aChar);
if(kRightBrace==aChar) {
aString+=kRightBrace; //append rightbrace, and...
aScanner.GetChar(aChar);//yank the closing right-brace
}
else
{
result=aScanner->ReadWhile(aString,gIdentChars,PR_FALSE);
aScanner->Peek(aChar);
if (kSemicolon == aChar) {
// consume semicolon that stopped the scan
aScanner->GetChar(aChar);
}
}
else
{
result=aScanner.ReadWhile(aString,gIdentChars,PR_FALSE);
aScanner.Peek(aChar);
if (kSemicolon == aChar) {
// consume semicolon that stopped the scan
aScanner.GetChar(aChar);
}
}
return result;
@ -1236,14 +1195,14 @@ PRInt32 CSkippedContentToken::GetTokenType(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CSkippedContentToken::Consume(PRUnichar aChar,CScanner* aScanner) {
PRInt32 CSkippedContentToken::Consume(PRUnichar aChar,CScanner& aScanner) {
PRBool done=PR_FALSE;
PRInt32 result=kNoError;
nsString temp;
while((!done) && (!aScanner->Eof())) {
while((!done) && (!aScanner.Eof())) {
static nsAutoString terminals(">");
result=aScanner->ReadUntil(temp,terminals,PR_TRUE);
result=aScanner.ReadUntil(temp,terminals,PR_TRUE);
done=PRBool(kNotFound!=temp.RFind(mTextValue,PR_TRUE));
}
mTextValue=temp;

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

@ -106,8 +106,8 @@ enum eHTMLAttributes {
eHTMLAttr_title, eHTMLAttr_wordbreak, eHTMLAttr_width, eHTMLAttr_xmp
};
PRInt32 ConsumeQuotedString(PRUnichar aChar,nsString& aString,CScanner* aScanner);
PRInt32 ConsumeAttributeText(PRUnichar aChar,nsString& aString,CScanner* aScanner);
PRInt32 ConsumeQuotedString(PRUnichar aChar,nsString& aString,CScanner& aScanner);
PRInt32 ConsumeAttributeText(PRUnichar aChar,nsString& aString,CScanner& aScanner);
PRInt32 FindEntityIndex(const char* aBuffer,PRInt32 aBufLen=-1);
eHTMLTags DetermineHTMLTagType(const nsString& aString);
eHTMLTokenTypes DetermineTokenType(const nsString& aString);
@ -139,7 +139,7 @@ protected:
class CStartToken: public CHTMLToken {
public:
CStartToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual eHTMLTags GetHTMLTag();
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
@ -163,7 +163,7 @@ class CStartToken: public CHTMLToken {
class CEndToken: public CHTMLToken {
public:
CEndToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual eHTMLTags GetHTMLTag();
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
@ -182,7 +182,7 @@ class CEndToken: public CHTMLToken {
class CCommentToken: public CHTMLToken {
public:
CCommentToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
char mLeadingChar;
@ -202,8 +202,8 @@ class CEntityToken : public CHTMLToken {
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
PRInt32 TranslateToUnicodeStr(nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
static PRInt32 ConsumeEntity(PRUnichar aChar,nsString& aString,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
static PRInt32 ConsumeEntity(PRUnichar aChar,nsString& aString,CScanner& aScanner);
static PRInt32 TranslateToUnicodeStr(PRInt32 aValue,nsString& aString);
static PRInt32 FindEntityIndex(const char* aBuffer,PRInt32 aBufLen=-1);
static PRBool VerifyEntityTable(void);
@ -226,7 +226,7 @@ class CEntityToken : public CHTMLToken {
class CWhitespaceToken: public CHTMLToken {
public:
CWhitespaceToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
};
@ -242,7 +242,7 @@ class CWhitespaceToken: public CHTMLToken {
class CTextToken: public CHTMLToken {
public:
CTextToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
};
@ -259,7 +259,7 @@ class CTextToken: public CHTMLToken {
class CAttributeToken: public CHTMLToken {
public:
CAttributeToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
virtual nsString& GetKey(void) {return mTextKey;}
@ -282,7 +282,7 @@ class CAttributeToken: public CHTMLToken {
class CNewlineToken: public CHTMLToken {
public:
CNewlineToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
};
@ -334,7 +334,7 @@ class CStyleToken: public CHTMLToken {
class CSkippedContentToken: public CAttributeToken {
public:
CSkippedContentToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
protected:

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

@ -77,10 +77,11 @@ class nsIDTD : public nsISupports {
* tag can contain newlines. Most do not.
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool CanDisregard(PRInt32 aParent,PRInt32 aChild)const=0;
virtual PRBool CanOmit(PRInt32 aParent,PRInt32 aChild)const=0;
/** -------------------------------------------------------
* This method does two things: 1st, help construct
@ -92,6 +93,18 @@ class nsIDTD : public nsISupports {
*/ //----------------------------------------------------
virtual PRInt32 GetDefaultParentTagFor(PRInt32 aTag) const=0;
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
virtual PRInt32 CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const=0;
};

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

@ -51,7 +51,7 @@ class nsIParser : public nsISupports {
public:
virtual void SetContentSink(nsIContentSink* aContentSink)=0;
virtual nsIContentSink* SetContentSink(nsIContentSink* aContentSink)=0;
virtual PRBool Parse(nsIURL* aURL)=0;
virtual PRBool ResumeParse()=0;
};

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

@ -39,6 +39,7 @@
#define ITOKENIZERDELEGATE
#include "prtypes.h"
#include "nsParserTypes.h"
class CScanner;
class CToken;
@ -49,8 +50,10 @@ class ITokenizerDelegate {
virtual PRBool WillTokenize()=0;
virtual PRBool DidTokenize()=0;
virtual CToken* GetToken(CScanner* aScanner,PRInt32& anErrorCode)=0;
virtual CToken* GetToken(CScanner& aScanner,PRInt32& anErrorCode)=0;
virtual PRBool WillAddToken(CToken& aToken)=0;
virtual eParseMode GetParseMode() const=0;
};
#endif

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

@ -33,7 +33,12 @@
#include "prtypes.h"
#define PRChar char
enum eParseMode {
eParseMode_unknown=0,
eParseMode_navigator,
eParseMode_other
};
const PRInt32 kNotFound = -1;
const PRInt32 kNoError = 0;

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

@ -32,11 +32,12 @@ const char* kBadHTMLText2="</BODY></HTML>";
* @param aURL -- pointer to URL to be loaded
* @return
*------------------------------------------------------*/
CScanner::CScanner(nsIURL* aURL) : mBuffer("") {
CScanner::CScanner(nsIURL* aURL,eParseMode aMode) : mBuffer("") {
NS_ASSERTION(0!=aURL,"Error: Null URL!");
mOffset=0;
mStream=0;
mTotalRead=0;
mParseMode=aMode;
if(aURL) {
PRInt32 error;
gURLRef=aURL->GetSpec();

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

@ -43,7 +43,7 @@ class ifstream;
class CScanner {
public:
CScanner(nsIURL* aURL);
CScanner(nsIURL* aURL,eParseMode aMode=eParseMode_navigator);
~CScanner();
PRInt32 GetChar(PRUnichar& ch);
@ -69,6 +69,7 @@ class CScanner {
nsString mBuffer;
PRInt32 mOffset;
PRInt32 mTotalRead;
eParseMode mParseMode;
};
#endif

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

@ -47,7 +47,7 @@ CToken::~CToken() {
* @param aScanner -- object to retrieve data from
* @return int error code
*------------------------------------------------------*/
PRInt32 CToken::Consume(PRUnichar aChar,CScanner* aScanner) {
PRInt32 CToken::Consume(PRUnichar aChar,CScanner& aScanner) {
PRInt32 result=kNoError;
return result;
}

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

@ -60,7 +60,7 @@ class CToken {
virtual void SetStringValue(const char* name);
virtual void SetOrdinal(PRInt32 value);
virtual PRInt32 GetOrdinal(void);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual void DebugDumpToken(ostream& out);
virtual void DebugDumpSource(ostream& out);
virtual PRInt32 GetTokenType(void);

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

@ -0,0 +1,637 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/1/98
*
*/
#include "nsTokenHandler.h"
#include "nsHTMLParser.h"
#include "nsHTMLTokens.h"
#include "nsDebug.h"
static const char* kNullParserGiven = "Error: Null parser given as argument";
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CTokenHandler::CTokenHandler(eHTMLTokenTypes aType) {
mType=aType;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CTokenHandler::~CTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
eHTMLTokenTypes CTokenHandler::GetTokenType(void){
return mType;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
PRBool result=PR_FALSE;
if(aParser){
result=PR_TRUE;
}
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CStartTokenHandler::CStartTokenHandler() : CTokenHandler(eToken_start) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CStartTokenHandler::~CStartTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CStartTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleStartToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CStartTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CEndTokenHandler::CEndTokenHandler(): CTokenHandler(eToken_end) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CEndTokenHandler::~CEndTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CEndTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleEndToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CEndTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CCommentTokenHandler::CCommentTokenHandler() : CTokenHandler(eToken_comment) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CCommentTokenHandler::~CCommentTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CCommentTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleCommentToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CCommentTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CEntityTokenHandler::CEntityTokenHandler() : CTokenHandler(eToken_entity) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CEntityTokenHandler::~CEntityTokenHandler() {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CEntityTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleEntityToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CEntityTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CWhitespaceTokenHandler::CWhitespaceTokenHandler() : CTokenHandler(eToken_whitespace) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CWhitespaceTokenHandler::~CWhitespaceTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CWhitespaceTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleWhitespaceToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CWhitespaceTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CNewlineTokenHandler::CNewlineTokenHandler() : CTokenHandler(eToken_newline) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CNewlineTokenHandler::~CNewlineTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CNewlineTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleNewlineToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CNewlineTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CTextTokenHandler::CTextTokenHandler() : CTokenHandler(eToken_text) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CTextTokenHandler::~CTextTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CTextTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleTextToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CTextTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CAttributeTokenHandler::CAttributeTokenHandler() : CTokenHandler(eToken_attribute) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CAttributeTokenHandler::~CAttributeTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CAttributeTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleAttributeToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CAttributeTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CScriptTokenHandler::CScriptTokenHandler() : CTokenHandler(eToken_script) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CScriptTokenHandler::~CScriptTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CScriptTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleScriptToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CScriptTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CStyleTokenHandler::CStyleTokenHandler() : CTokenHandler(eToken_style) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CStyleTokenHandler::~CStyleTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CStyleTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleStyleToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CStyleTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CSkippedContentTokenHandler::CSkippedContentTokenHandler() : CTokenHandler(eToken_skippedcontent) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CSkippedContentTokenHandler::~CSkippedContentTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CSkippedContentTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleSkippedContentToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CSkippedContentTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}

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

@ -0,0 +1,161 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/1/98
*
*/
#ifndef CTokenHandler__
#define CTokenHandler__
#include "prtypes.h"
#include "nsString.h"
#include "nsHTMLTokens.h"
#include "nsITokenHandler.h"
class CToken;
class nsHTMLParser;
class CTokenHandler : public CITokenHandler {
public:
CTokenHandler(eHTMLTokenTypes aType=eToken_unknown);
virtual ~CTokenHandler();
virtual eHTMLTokenTypes GetTokenType(void);
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
protected:
eHTMLTokenTypes mType;
};
class CStartTokenHandler : public CTokenHandler {
public:
CStartTokenHandler();
virtual ~CStartTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CEndTokenHandler : public CTokenHandler {
public:
CEndTokenHandler();
virtual ~CEndTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CCommentTokenHandler : public CTokenHandler {
public:
CCommentTokenHandler();
virtual ~CCommentTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CEntityTokenHandler : public CTokenHandler {
public:
CEntityTokenHandler();
virtual ~CEntityTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CWhitespaceTokenHandler : public CTokenHandler {
public:
CWhitespaceTokenHandler();
virtual ~CWhitespaceTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CNewlineTokenHandler : public CTokenHandler {
public:
CNewlineTokenHandler();
virtual ~CNewlineTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CTextTokenHandler : public CTokenHandler {
public:
CTextTokenHandler();
virtual ~CTextTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CAttributeTokenHandler : public CTokenHandler {
public:
CAttributeTokenHandler();
virtual ~CAttributeTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CScriptTokenHandler : public CTokenHandler {
public:
CScriptTokenHandler();
virtual ~CScriptTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CStyleTokenHandler : public CTokenHandler {
public:
CStyleTokenHandler();
virtual ~CStyleTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CSkippedContentTokenHandler : public CTokenHandler {
public:
CSkippedContentTokenHandler();
virtual ~CSkippedContentTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
#endif

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

@ -19,7 +19,6 @@
#include <fstream.h>
#include "nsTokenizer.h"
#include "nsITokenizerDelegate.h"
#include "nsToken.h"
#include "nsScanner.h"
#include "nsIURL.h"
@ -33,10 +32,11 @@
* @param aDelegate -- ref to delegate to be used to tokenize
* @return
*------------------------------------------------------*/
CTokenizer::CTokenizer(nsIURL* aURL,ITokenizerDelegate& aDelegate) :
mDelegate(aDelegate),
CTokenizer::CTokenizer(nsIURL* aURL,ITokenizerDelegate* aDelegate,eParseMode aMode) :
mTokenDeque() {
mScanner= new CScanner(aURL);
mDelegate=aDelegate;
mScanner=new CScanner(aURL,aMode);
mParseMode=aMode;
}
@ -48,6 +48,20 @@ CTokenizer::CTokenizer(nsIURL* aURL,ITokenizerDelegate& aDelegate) :
* @return
*------------------------------------------------------*/
CTokenizer::~CTokenizer() {
delete mScanner;
delete mDelegate;
mScanner=0;
}
/**
* Retrieve a reference to the internal token deque.
*
* @update gess 4/20/98
* @return deque reference
*/
nsDeque& CTokenizer::GetDeque(void) {
return mTokenDeque;
}
/**-------------------------------------------------------
@ -59,7 +73,7 @@ CTokenizer::~CTokenizer() {
* @return new token or null
*------------------------------------------------------*/
CToken* CTokenizer::GetToken(PRInt32& anError) {
CToken* nextToken=mDelegate.GetToken(mScanner,anError);
CToken* nextToken=mDelegate->GetToken(*mScanner,anError);
return nextToken;
}
@ -86,7 +100,7 @@ PRInt32 CTokenizer::GetSize(void) {
*------------------------------------------------------*/
PRBool CTokenizer::WillTokenize(){
PRBool result=PR_TRUE;
result=mDelegate.WillTokenize();
result=mDelegate->WillTokenize();
return result;
}
@ -110,7 +124,7 @@ PRInt32 CTokenizer::Tokenize(void) {
#ifdef VERBOSE_DEBUG
nextToken->DebugDumpToken(cout);
#endif
if(mDelegate.WillAddToken(*nextToken)) {
if(mDelegate->WillAddToken(*nextToken)) {
mTokenDeque.Push(nextToken);
}
}
@ -131,7 +145,12 @@ PRInt32 CTokenizer::Tokenize(void) {
* @return TRUE if all went well
*------------------------------------------------------*/
PRBool CTokenizer::DidTokenize() {
PRBool result=mDelegate.DidTokenize();
PRBool result=mDelegate->DidTokenize();
#ifdef VERBOSE_DEBUG
DebugDumpTokens(cout);
#endif
return result;
}
@ -145,12 +164,12 @@ PRBool CTokenizer::DidTokenize() {
* @return
*------------------------------------------------------*/
void CTokenizer::DebugDumpTokens(ostream& out) {
CDequeIterator b=mTokenDeque.Begin();
CDequeIterator e=mTokenDeque.End();
nsDequeIterator b=mTokenDeque.Begin();
nsDequeIterator e=mTokenDeque.End();
CToken* theToken;
while(b!=e) {
theToken=(b++);
theToken=(CToken*)(b++);
theToken->DebugDumpToken(out);
}
}
@ -166,12 +185,12 @@ void CTokenizer::DebugDumpTokens(ostream& out) {
* @return
*------------------------------------------------------*/
void CTokenizer::DebugDumpSource(ostream& out) {
CDequeIterator b=mTokenDeque.Begin();
CDequeIterator e=mTokenDeque.End();
nsDequeIterator b=mTokenDeque.Begin();
nsDequeIterator e=mTokenDeque.End();
CToken* theToken;
while(b!=e) {
theToken=(b++);
theToken=(CToken*)(b++);
theToken->DebugDumpSource(out);
}

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

@ -50,13 +50,13 @@ class nsIURL;
class CTokenizer {
public:
CTokenizer(nsIURL* aURL,ITokenizerDelegate& aDelegate);
CTokenizer(nsIURL* aURL,ITokenizerDelegate* aDelegate,eParseMode aMode);
~CTokenizer();
PRInt32 Tokenize(void);
CToken* GetToken(PRInt32& anErrorCode);
PRInt32 GetSize(void);
CDeque& GetDeque(void) {return mTokenDeque;}
nsDeque& GetDeque(void);
void DebugDumpSource(ostream& out);
void DebugDumpTokens(ostream& out);
@ -67,9 +67,10 @@ class CTokenizer {
PRBool WillTokenize();
PRBool DidTokenize();
ITokenizerDelegate& mDelegate;
ITokenizerDelegate* mDelegate;
CScanner* mScanner;
CDeque mTokenDeque;
nsDeque mTokenDeque;
eParseMode mParseMode;
};
#endif

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

@ -0,0 +1,298 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/8/98
*
*
*/
#include "CNavDTD.h"
#include "nsHTMLTokens.h"
#include "nsCRT.h"
#include "nsParserTypes.h"
static NS_DEFINE_IID(kISupportsIID, NS_ISUPPORTS_IID);
static NS_DEFINE_IID(kIDTDIID, NS_IDTD_IID);
static NS_DEFINE_IID(kHTMLDTDIID, NS_IHTML_DTD_IID);
static NS_DEFINE_IID(kClassIID, NS_INAVHTML_DTD_IID);
/**-------------------------------------------------------
* This method gets called as part of our COM-like interfaces.
* Its purpose is to create an interface to parser object
* of some type.
*
* @update gess 4/8/98
* @param nsIID id of object to discover
* @param aInstancePtr ptr to newly discovered interface
* @return NS_xxx result code
*------------------------------------------------------*/
nsresult CNavDTD::QueryInterface(const nsIID& aIID, void** aInstancePtr)
{
if (NULL == aInstancePtr) {
return NS_ERROR_NULL_POINTER;
}
if(aIID.Equals(kISupportsIID)) { //do IUnknown...
*aInstancePtr = (nsIDTD*)(this);
}
else if(aIID.Equals(kIDTDIID)) { //do IParser base class...
*aInstancePtr = (nsIDTD*)(this);
}
else if(aIID.Equals(kClassIID)) { //do this class...
*aInstancePtr = (CNavDTD*)(this);
}
else {
*aInstancePtr=0;
return NS_NOINTERFACE;
}
((nsISupports*) *aInstancePtr)->AddRef();
return NS_OK;
}
/**-------------------------------------------------------
* This method is defined in nsIParser. It is used to
* cause the COM-like construction of an nsHTMLParser.
*
* @update gess 4/8/98
* @param nsIParser** ptr to newly instantiated parser
* @return NS_xxx error result
*------------------------------------------------------*/
NS_HTMLPARS nsresult NS_NewNavHTMLDTD(nsIDTD** aInstancePtrResult)
{
CNavDTD* it = new CNavDTD();
if (it == 0) {
return NS_ERROR_OUT_OF_MEMORY;
}
return it->QueryInterface(kClassIID, (void **) aInstancePtrResult);
}
NS_IMPL_ADDREF(CNavDTD)
NS_IMPL_RELEASE(CNavDTD)
/**-------------------------------------------------------
* Default constructor
*
* @update gess 4/9/98
* @param
* @return
*------------------------------------------------------*/
CNavDTD::CNavDTD() : nsHTMLDTD() {
}
/**-------------------------------------------------------
* Default destructor
*
* @update gess 4/9/98
* @param
* @return
*------------------------------------------------------*/
CNavDTD::~CNavDTD(){
}
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 4/8/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
PRBool CNavDTD::CanContain(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=nsHTMLDTD::CanContain(aParent,aChild);
return result;
}
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 4/8/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
PRBool CNavDTD::CanContainIndirect(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=nsHTMLDTD::CanContainIndirect(aParent,aChild);
return result;
}
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag can contain newlines. Most do not.
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
PRBool CNavDTD::CanOmit(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=PR_FALSE;
switch((eHTMLTags)aParent) {
case eHTMLTag_tr:
case eHTMLTag_table:
case eHTMLTag_thead:
case eHTMLTag_tfoot:
case eHTMLTag_tbody:
case eHTMLTag_col:
case eHTMLTag_colgroup:
if((aChild==eHTMLTag_newline) ||
(aChild==eHTMLTag_whitespace))
result=PR_TRUE;
break;
default:
result=PR_FALSE;
break;
}
return result;
}
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag is itself a container
*
* @update gess 4/8/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
PRBool CNavDTD::IsContainer(PRInt32 aTag) const {
PRBool result=nsHTMLDTD::IsContainer(aTag);
return result;
}
/*-------------------------------------------------------
* This method does two things: 1st, help construct
* our own internal model of the content-stack; and
* 2nd, pass this message on to the sink.
* @update gess4/6/98
* @param aNode -- next node to be added to model
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRInt32 CNavDTD::GetDefaultParentTagFor(PRInt32 aTag) const{
eHTMLTags result=eHTMLTag_unknown;
switch(aTag) {
case eHTMLTag_html:
result=(eHTMLTags)kNotFound; break;
case eHTMLTag_body:
case eHTMLTag_head:
case eHTMLTag_header:
case eHTMLTag_footer:
case eHTMLTag_frameset:
result=eHTMLTag_html; break;
//These tags are head specific...
case eHTMLTag_style:
case eHTMLTag_meta:
case eHTMLTag_title:
case eHTMLTag_base:
case eHTMLTag_link:
result=eHTMLTag_head; break;
//These tags are table specific...
case eHTMLTag_caption:
case eHTMLTag_colgroup:
case eHTMLTag_tbody:
case eHTMLTag_tfoot:
case eHTMLTag_thead:
case eHTMLTag_tr:
result=eHTMLTag_table; break;
case eHTMLTag_td:
case eHTMLTag_th:
result=eHTMLTag_tr; break;
case eHTMLTag_col:
result=eHTMLTag_colgroup; break;
//These have to do with listings...
case eHTMLTag_listitem:
result=eHTMLTag_ul; break;
case eHTMLTag_dd:
case eHTMLTag_dt:
result=eHTMLTag_dl; break;
case eHTMLTag_option:
result=eHTMLTag_select; break;
//These have to do with image maps...
case eHTMLTag_area:
result=eHTMLTag_map; break;
//These have to do with applets...
case eHTMLTag_param:
result=eHTMLTag_applet; break;
//These have to do with frames...
case eHTMLTag_frame:
result=eHTMLTag_frameset; break;
default:
result=eHTMLTag_body; //XXX Hack! Just for now.
break;
}
return result;
}
/** ------------------------------------------------------
* This method gets called at various times by the parser
* whenever we want to verify a valid context stack. This
* method also gives us a hook to add debugging metrics.
*
* @update gess4/6/98
* @param aStack[] array of ints (tokens)
* @param aCount number of elements in given array
* @return TRUE if stack is valid, else FALSE
*/ //-----------------------------------------------------
PRBool CNavDTD::VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const {
PRBool result=PR_TRUE;
if(aCount>0) {
}
return result;
}
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
PRInt32 CNavDTD::CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const {
PRInt32 result=0;
return result;
}

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

@ -0,0 +1,147 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/8/98
*
*
*/
#ifndef NS_NAVHTMLDTD__
#define NS_NAVHTMLDTD__
#include "nsHTMLDTD.h"
#include "nsHTMLTokens.h"
#include "nshtmlpars.h"
#define NS_INAVHTML_DTD_IID \
{0x5c5cce40, 0xcfd6, 0x11d1, \
{0xaa, 0xda, 0x00, 0x80, 0x5f, 0x8a, 0x3e, 0x14}}
class CNavDTD : public nsHTMLDTD {
public:
NS_DECL_ISUPPORTS
/** -------------------------------------------------------
*
*
* @update gess 4/9/98
* @param
* @return
*/ //------------------------------------------------------
CNavDTD();
/** -------------------------------------------------------
*
*
* @update gess 4/9/98
* @param
* @return
*/ //------------------------------------------------------
virtual ~CNavDTD();
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 3/25/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
virtual PRBool CanContain(PRInt32 aParent,PRInt32 aChild) const;
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 3/25/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
virtual PRBool CanContainIndirect(PRInt32 aParent,PRInt32 aChild) const;
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag can contain newlines. Most do not.
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool CanOmit(PRInt32 aParent,PRInt32 aChild)const;
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag is itself a container
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool IsContainer(PRInt32 aTags) const;
/** ------------------------------------------------------
* This method does two things: 1st, help construct
* our own internal model of the content-stack; and
* 2nd, pass this message on to the sink.
* @update gess4/6/98
* @param aNode -- next node to be added to model
* @return TRUE if ok, FALSE if error
*/ //----------------------------------------------------
virtual PRInt32 GetDefaultParentTagFor(PRInt32 aTag) const;
/** ------------------------------------------------------
* This method gets called at various times by the parser
* whenever we want to verify a valid context stack. This
* method also gives us a hook to add debugging metrics.
*
* @update gess4/6/98
* @param aStack[] array of ints (tokens)
* @param aCount number of elements in given array
* @return TRUE if stack is valid, else FALSE
*/ //-----------------------------------------------------
virtual PRBool VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const;
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
virtual PRInt32 CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const;
};
#endif

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

@ -0,0 +1,232 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
#include <ctype.h>
#include "CNavDelegate.h"
#include "nsHTMLTokens.h"
#include "nsScanner.h"
#include "nsParserTypes.h"
// Note: We already handle the following special case conditions:
// 1) If you see </>, simply treat it as a bad tag.
// 2) If you see </ ...>, treat it like a comment.
// 3) If you see <> or <_ (< space) simply treat it as text.
// 4) If you see <~ (< followed by non-alpha), treat it as text.
static char gIdentChars[] = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_";
/**-------------------------------------------------------
* Default constructor
*
* @updated gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
CNavDelegate::CNavDelegate() : CHTMLTokenizerDelegate(){
}
/**-------------------------------------------------------
* Default constructor
*
* @updated gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
CNavDelegate::CNavDelegate(CNavDelegate& aDelegate) : CHTMLTokenizerDelegate() {
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
eParseMode CNavDelegate::GetParseMode() const {
return eParseMode_navigator;
}
/**-------------------------------------------------------
* This method is called just after a "<" has been consumed
* and we know we're at the start of some kind of tagged
* element. We don't know yet if it's a tag or a comment.
*
* @update gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
CToken* CNavDelegate::ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CToken* result=0;
nsAutoString empty("");
anErrorCode=anErrorCode=aScanner.GetChar(aChar);
switch(aChar) {
case kForwardSlash:
PRUnichar ch;
anErrorCode=aScanner.Peek(ch);
if(nsString::IsAlpha(ch))
result=new CEndToken(empty);
else result=new CCommentToken(empty); //Special case: </ ...> is treated as a comment
break;
case kExclamation:
result=new CCommentToken(empty);
break;
default:
if(nsString::IsAlpha(aChar))
return ConsumeStartTag(aChar,aScanner,anErrorCode);
else if(kNotFound!=aChar) {
nsAutoString temp("<");
return ConsumeText(temp,aScanner,anErrorCode);
}
}
if(result!=0) {
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(anErrorCode) {
result=0;
delete result;
}
}
return result;
}
/*-------------------------------------------------------
* This is a special case method. It's job is to consume
* all of the given tag up to an including the end tag.
*
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* CNavDelegate::ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode){
//In the case that we just read the given tag, we should go and
//consume all the input until we find a matching end tag.
nsAutoString endTag("</");
endTag.Append(aString);
endTag.Append(">");
CSkippedContentToken* sc=new CSkippedContentToken(endTag);
anErrorCode= sc->Consume(aChar,aScanner); //tell new token to finish consuming text...
return sc;
}
/**-------------------------------------------------------
* This method is called just after a "<" has been consumed
* and we know we're at the start of a tag.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* CNavDelegate::ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CStartToken* result=new CStartToken(nsAutoString(""));
if(result) {
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(result->IsAttributed())
ConsumeAttributes(aChar,aScanner,anErrorCode);
//now that that's over with, we have one more problem to solve.
//In the case that we just read a <SCRIPT> or <STYLE> tags, we should go and
//consume all the content itself.
nsString& str=result->GetText();
if(str.EqualsIgnoreCase("SCRIPT") ||
str.EqualsIgnoreCase("STYLE") ||
str.EqualsIgnoreCase("TITLE")) {
CToken* sc=ConsumeContentToEndTag(str,aChar,aScanner,anErrorCode);
if(sc){
//now we strip the ending sequence from our new SkippedContent token...
PRInt32 slen=str.Length()+3;
nsString& skippedText=sc->GetText();
skippedText.Cut(skippedText.Length()-slen,slen);
mTokenDeque.Push(sc);
//In the case that we just read a given tag, we should go and
//consume all the tag content itself (and throw it all away).
CEndToken* endtoken=new CEndToken(str);
mTokenDeque.Push(endtoken);
}
}
}
return result;
}
/**-------------------------------------------------------
* This method is called just after a "&" has been consumed
* and we know we're at the start of an entity.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* CNavDelegate::ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CToken* result = 0;
PRUnichar ch;
anErrorCode=aScanner.GetChar(ch);
if(nsString::IsAlpha(ch)) { //handle common enity references &xxx; or &#000.
result = new CEntityToken(nsAutoString(""));
anErrorCode= result->Consume(ch,aScanner); //tell new token to finish consuming text...
}
else if(kHashsign==ch) {
result = new CEntityToken(nsAutoString(""));
anErrorCode=result->Consume(ch,aScanner);
}
else
{
//oops, we're actually looking at plain text...
nsAutoString temp("&");
return ConsumeText(temp,aScanner,anErrorCode);
}
return result;
}
/**-------------------------------------------------------
* This method repeatedly called by the tokenizer.
* Each time, we determine the kind of token were about to
* read, and then we call the appropriate method to handle
* that token type.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* CNavDelegate::GetToken(CScanner& aScanner,PRInt32& anErrorCode) {
return CHTMLTokenizerDelegate::GetToken(aScanner,anErrorCode);
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
CToken* CNavDelegate::CreateTokenOfType(eHTMLTokenTypes aType) {
return 0;
}

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

@ -0,0 +1,70 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/1/98
*
* This class is used as the HTML tokenizer delegate for
* netscape navigator compatibility.
*
* The tokenzier class has the smarts to open an source,
* and iterate over its characters to produce a list of
* tokens. The tokenizer doesn't know HTML, which is
* where this delegate comes into play.
*
* The tokenizer calls methods on this class to help
* with the creation of HTML-specific tokens from a source
* stream.
*
* The interface here is very simple, mainly the call
* to GetToken(), which Consumes bytes from the underlying
* scanner.stream, and produces an HTML specific CToken.
*/
#ifndef __NAV_DELEGATE
#define __NAV_DELEGATE
#include "nsToken.h"
#include "nsHTMLDelegate.h"
class CNavDelegate : public CHTMLTokenizerDelegate {
public:
CNavDelegate();
CNavDelegate(CNavDelegate& aDelegate);
virtual CToken* GetToken(CScanner& aScanner,PRInt32& anErrorCode);
virtual eParseMode GetParseMode() const;
protected:
virtual CToken* ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
//the only special case method...
virtual CToken* ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* CreateTokenOfType(eHTMLTokenTypes aType);
};
#endif

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

@ -0,0 +1,298 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/8/98
*
*
*/
#include "COtherDTD.h"
#include "nsHTMLTokens.h"
#include "nsCRT.h"
#include "nsParserTypes.h"
static NS_DEFINE_IID(kISupportsIID, NS_ISUPPORTS_IID);
static NS_DEFINE_IID(kIDTDIID, NS_IDTD_IID);
static NS_DEFINE_IID(kHTMLDTDIID, NS_IHTML_DTD_IID);
static NS_DEFINE_IID(kClassIID, NS_IOtherHTML_DTD_IID);
/**-------------------------------------------------------
* This method gets called as part of our COM-like interfaces.
* Its purpose is to create an interface to parser object
* of some type.
*
* @update gess 4/8/98
* @param nsIID id of object to discover
* @param aInstancePtr ptr to newly discovered interface
* @return NS_xxx result code
*------------------------------------------------------*/
nsresult COtherDTD::QueryInterface(const nsIID& aIID, void** aInstancePtr)
{
if (NULL == aInstancePtr) {
return NS_ERROR_NULL_POINTER;
}
if(aIID.Equals(kISupportsIID)) { //do IUnknown...
*aInstancePtr = (nsIDTD*)(this);
}
else if(aIID.Equals(kIDTDIID)) { //do IParser base class...
*aInstancePtr = (nsIDTD*)(this);
}
else if(aIID.Equals(kClassIID)) { //do this class...
*aInstancePtr = (COtherDTD*)(this);
}
else {
*aInstancePtr=0;
return NS_NOINTERFACE;
}
((nsISupports*) *aInstancePtr)->AddRef();
return NS_OK;
}
/**-------------------------------------------------------
* This method is defined in nsIParser. It is used to
* cause the COM-like construction of an nsHTMLParser.
*
* @update gess 4/8/98
* @param nsIParser** ptr to newly instantiated parser
* @return NS_xxx error result
*------------------------------------------------------*/
NS_HTMLPARS nsresult NS_NewOtherHTMLDTD(nsIDTD** aInstancePtrResult)
{
COtherDTD* it = new COtherDTD();
if (it == 0) {
return NS_ERROR_OUT_OF_MEMORY;
}
return it->QueryInterface(kClassIID, (void **) aInstancePtrResult);
}
NS_IMPL_ADDREF(COtherDTD)
NS_IMPL_RELEASE(COtherDTD)
/**-------------------------------------------------------
* Default constructor
*
* @update gess 4/9/98
* @param
* @return
*------------------------------------------------------*/
COtherDTD::COtherDTD() : nsHTMLDTD() {
}
/**-------------------------------------------------------
* Default destructor
*
* @update gess 4/9/98
* @param
* @return
*------------------------------------------------------*/
COtherDTD::~COtherDTD(){
}
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 4/8/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
PRBool COtherDTD::CanContain(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=nsHTMLDTD::CanContain(aParent,aChild);
return result;
}
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 4/8/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
PRBool COtherDTD::CanContainIndirect(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=nsHTMLDTD::CanContainIndirect(aParent,aChild);
return result;
}
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag can contain newlines. Most do not.
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
PRBool COtherDTD::CanOmit(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=PR_FALSE;
switch((eHTMLTags)aParent) {
case eHTMLTag_tr:
case eHTMLTag_table:
case eHTMLTag_thead:
case eHTMLTag_tfoot:
case eHTMLTag_tbody:
case eHTMLTag_col:
case eHTMLTag_colgroup:
if((aChild==eHTMLTag_newline) ||
(aChild==eHTMLTag_whitespace))
result=PR_TRUE;
break;
default:
result=PR_FALSE;
break;
}
return result;
}
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag is itself a container
*
* @update gess 4/8/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
PRBool COtherDTD::IsContainer(PRInt32 aTag) const {
PRBool result=nsHTMLDTD::IsContainer(aTag);
return result;
}
/*-------------------------------------------------------
* This method does two things: 1st, help construct
* our own internal model of the content-stack; and
* 2nd, pass this message on to the sink.
* @update gess4/6/98
* @param aNode -- next node to be added to model
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRInt32 COtherDTD::GetDefaultParentTagFor(PRInt32 aTag) const{
eHTMLTags result=eHTMLTag_unknown;
switch(aTag) {
case eHTMLTag_html:
result=(eHTMLTags)kNotFound; break;
case eHTMLTag_body:
case eHTMLTag_head:
case eHTMLTag_header:
case eHTMLTag_footer:
case eHTMLTag_frameset:
result=eHTMLTag_html; break;
//These tags are head specific...
case eHTMLTag_style:
case eHTMLTag_meta:
case eHTMLTag_title:
case eHTMLTag_base:
case eHTMLTag_link:
result=eHTMLTag_head; break;
//These tags are table specific...
case eHTMLTag_caption:
case eHTMLTag_colgroup:
case eHTMLTag_tbody:
case eHTMLTag_tfoot:
case eHTMLTag_thead:
case eHTMLTag_tr:
result=eHTMLTag_table; break;
case eHTMLTag_td:
case eHTMLTag_th:
result=eHTMLTag_tr; break;
case eHTMLTag_col:
result=eHTMLTag_colgroup; break;
//These have to do with listings...
case eHTMLTag_listitem:
result=eHTMLTag_ul; break;
case eHTMLTag_dd:
case eHTMLTag_dt:
result=eHTMLTag_dl; break;
case eHTMLTag_option:
result=eHTMLTag_select; break;
//These have to do with image maps...
case eHTMLTag_area:
result=eHTMLTag_map; break;
//These have to do with applets...
case eHTMLTag_param:
result=eHTMLTag_applet; break;
//These have to do with frames...
case eHTMLTag_frame:
result=eHTMLTag_frameset; break;
default:
result=eHTMLTag_body; //XXX Hack! Just for now.
break;
}
return result;
}
/** ------------------------------------------------------
* This method gets called at various times by the parser
* whenever we want to verify a valid context stack. This
* method also gives us a hook to add debugging metrics.
*
* @update gess4/6/98
* @param aStack[] array of ints (tokens)
* @param aCount number of elements in given array
* @return TRUE if stack is valid, else FALSE
*/ //-----------------------------------------------------
PRBool COtherDTD::VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const {
PRBool result=PR_TRUE;
if(aCount>0) {
}
return result;
}
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
PRInt32 COtherDTD::CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const {
PRInt32 result=0;
return result;
}

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

@ -0,0 +1,148 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/8/98
*
*
*/
#ifndef NS_OTHERHTMLDTD__
#define NS_OTHERHTMLDTD__
#include "nsHTMLDTD.h"
#include "nsHTMLTokens.h"
#include "nshtmlpars.h"
#define NS_IOtherHTML_DTD_IID \
{0x8a5e89c0, 0xd16d, 0x11d1, \
{0x80, 0x22, 0x00, 0x60, 0x8, 0x14, 0x98, 0x89}}
class COtherDTD : public nsHTMLDTD {
public:
NS_DECL_ISUPPORTS
/** -------------------------------------------------------
*
*
* @update gess 4/9/98
* @param
* @return
*/ //------------------------------------------------------
COtherDTD();
/** -------------------------------------------------------
*
*
* @update gess 4/9/98
* @param
* @return
*/ //------------------------------------------------------
virtual ~COtherDTD();
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 3/25/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
virtual PRBool CanContain(PRInt32 aParent,PRInt32 aChild) const;
/** ------------------------------------------------------
* This method is called to determine whether or not a tag
* of one type can contain a tag of another type.
*
* @update gess 3/25/98
* @param aParent -- tag enum of parent container
* @param aChild -- tag enum of child container
* @return PR_TRUE if parent can contain child
*/ //----------------------------------------------------
virtual PRBool CanContainIndirect(PRInt32 aParent,PRInt32 aChild) const;
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag can contain newlines. Most do not.
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool CanOmit(PRInt32 aParent,PRInt32 aChild)const;
/** -------------------------------------------------------
* This method gets called to determine whether a given
* tag is itself a container
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool IsContainer(PRInt32 aTags) const;
/** ------------------------------------------------------
* This method does two things: 1st, help construct
* our own internal model of the content-stack; and
* 2nd, pass this message on to the sink.
* @update gess4/6/98
* @param aNode -- next node to be added to model
* @return TRUE if ok, FALSE if error
*/ //----------------------------------------------------
virtual PRInt32 GetDefaultParentTagFor(PRInt32 aTag) const;
/** ------------------------------------------------------
* This method gets called at various times by the parser
* whenever we want to verify a valid context stack. This
* method also gives us a hook to add debugging metrics.
*
* @update gess4/6/98
* @param aStack[] array of ints (tokens)
* @param aCount number of elements in given array
* @return TRUE if stack is valid, else FALSE
*/ //-----------------------------------------------------
virtual PRBool VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const;
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
virtual PRInt32 CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const;
};
#endif

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

@ -0,0 +1,235 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
#include <ctype.h>
#include "COtherDelegate.h"
#include "nsHTMLTokens.h"
#include "nsScanner.h"
#include "nsParserTypes.h"
// Note: We already handle the following special case conditions:
// 1) If you see </>, simply treat it as a bad tag.
// 2) If you see </ ...>, treat it like a comment.
// 3) If you see <> or <_ (< space) simply treat it as text.
// 4) If you see <~ (< followed by non-alpha), treat it as text.
static char gIdentChars[] = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_";
/**-------------------------------------------------------
* Default constructor
*
* @updated gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
COtherDelegate::COtherDelegate() : CHTMLTokenizerDelegate(){
}
/**-------------------------------------------------------
* Default constructor
*
* @updated gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
COtherDelegate::COtherDelegate(COtherDelegate& aDelegate) : CHTMLTokenizerDelegate(){
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
eParseMode COtherDelegate::GetParseMode() const {
return eParseMode_other;
}
/**-------------------------------------------------------
* This method is called just after a "<" has been consumed
* and we know we're at the start of some kind of tagged
* element. We don't know yet if it's a tag or a comment.
*
* @update gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
CToken* COtherDelegate::ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CToken* result=0;
nsAutoString empty("");
anErrorCode=anErrorCode=aScanner.GetChar(aChar);
switch(aChar) {
case kForwardSlash:
PRUnichar ch;
anErrorCode=aScanner.Peek(ch);
if(nsString::IsAlpha(ch))
result=new CEndToken(empty);
else result=new CCommentToken(empty); //Special case: </ ...> is treated as a comment
break;
case kExclamation:
result=new CCommentToken(empty);
break;
default:
if(nsString::IsAlpha(aChar))
return ConsumeStartTag(aChar,aScanner,anErrorCode);
else if(kNotFound!=aChar) {
nsAutoString temp("<");
return ConsumeText(temp,aScanner,anErrorCode);
}
}
if(result!=0) {
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(anErrorCode) {
result=0;
delete result;
}
}
return result;
}
/*-------------------------------------------------------
* This is a special case method. It's job is to consume
* all of the given tag up to an including the end tag.
*
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* COtherDelegate::ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode){
//In the case that we just read the given tag, we should go and
//consume all the input until we find a matching end tag.
nsAutoString endTag("</");
endTag.Append(aString);
endTag.Append(">");
CSkippedContentToken* sc=new CSkippedContentToken(endTag);
anErrorCode= sc->Consume(aChar,aScanner); //tell new token to finish consuming text...
return sc;
}
/**-------------------------------------------------------
* This method is called just after a "<" has been consumed
* and we know we're at the start of a tag.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* COtherDelegate::ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CStartToken* result=new CStartToken(nsAutoString(""));
if(result) {
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(result->IsAttributed())
ConsumeAttributes(aChar,aScanner,anErrorCode);
//now that that's over with, we have one more problem to solve.
//In the case that we just read a <SCRIPT> or <STYLE> tags, we should go and
//consume all the content itself.
nsString& str=result->GetText();
if(str.EqualsIgnoreCase("SCRIPT") ||
str.EqualsIgnoreCase("STYLE") ||
str.EqualsIgnoreCase("TITLE")) {
CToken* sc=ConsumeContentToEndTag(str,aChar,aScanner,anErrorCode);
if(sc){
//now we strip the ending sequence from our new SkippedContent token...
PRInt32 slen=str.Length()+3;
nsString& skippedText=sc->GetText();
skippedText.Cut(skippedText.Length()-slen,slen);
mTokenDeque.Push(sc);
//In the case that we just read a given tag, we should go and
//consume all the tag content itself (and throw it all away).
CEndToken* endtoken=new CEndToken(str);
mTokenDeque.Push(endtoken);
}
}
}
return result;
}
/**-------------------------------------------------------
* This method is called just after a "&" has been consumed
* and we know we're at the start of an entity.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* COtherDelegate::ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CToken* result = 0;
PRUnichar ch;
anErrorCode=aScanner.GetChar(ch);
if(nsString::IsAlpha(ch)) { //handle common enity references &xxx; or &#000.
result = new CEntityToken(nsAutoString(""));
anErrorCode= result->Consume(ch,aScanner); //tell new token to finish consuming text...
}
else if(kHashsign==ch) {
result = new CEntityToken(nsAutoString(""));
anErrorCode=result->Consume(ch,aScanner);
}
else
{
//oops, we're actually looking at plain text...
nsAutoString temp("&");
return ConsumeText(temp,aScanner,anErrorCode);
}
return result;
}
/**-------------------------------------------------------
* This method repeatedly called by the tokenizer.
* Each time, we determine the kind of token were about to
* read, and then we call the appropriate method to handle
* that token type.
*
* @update gess 3/25/98
* @param aChar: last char read
* @param aScanner: see nsScanner.h
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* COtherDelegate::GetToken(CScanner& aScanner,PRInt32& anErrorCode){
return CHTMLTokenizerDelegate::GetToken(aScanner,anErrorCode);
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
CToken* COtherDelegate::CreateTokenOfType(eHTMLTokenTypes aType) {
return 0;
}

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

@ -0,0 +1,71 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/1/98
*
* This class is used as the HTML tokenizer delegate for
* an alternate html browser.
*
* The tokenzier class has the smarts to open an source,
* and iterate over its characters to produce a list of
* tokens. The tokenizer doesn't know HTML, which is
* where this delegate comes into play.
*
* The tokenizer calls methods on this class to help
* with the creation of HTML-specific tokens from a source
* stream.
*
* The interface here is very simple, mainly the call
* to GetToken(), which Consumes bytes from the underlying
* scanner.stream, and produces an HTML specific CToken.
*/
#ifndef __OTHER_DELEGATE
#define __OTHER_DELEGATE
#include "nsToken.h"
#include "nsHTMLDelegate.h"
class COtherDelegate : public CHTMLTokenizerDelegate {
public:
COtherDelegate();
COtherDelegate(COtherDelegate& aDelegate);
virtual CToken* GetToken(CScanner& aScanner,PRInt32& anErrorCode);
virtual eParseMode GetParseMode() const;
protected:
virtual CToken* ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
//the only special case method...
virtual CToken* ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* CreateTokenOfType(eHTMLTokenTypes aType);
};
#endif

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

@ -22,17 +22,20 @@ LIBRARY_NAME = raptorhtmlpars
DEFINES = -D_IMPL_NS_HTMLPARS
CPPSRCS = \
nsDeque.cpp \
nsHTMLContentSink.cpp \
nsHTMLDelegate.cpp \
nsHTMLParser.cpp \
nsHTMLTokens.cpp \
nsParserNode.cpp \
nsScanner.cpp \
nsToken.cpp \
nsTokenizer.cpp \
nsDefaultTokenHandler.cpp \
nsTokenHandler.cpp \
nsHTMLParser.cpp \
nsHTMLTokens.cpp \
nsHTMLDelegate.cpp \
nsHTMLDTD.cpp \
CNavDelegate.cpp \
CNavDTD.cpp \
COtherDelegate.cpp \
COtherDTD.cpp \
$(NULL)
EXPORTS = \

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

@ -23,19 +23,23 @@ DEFINES=-D_IMPL_NS_HTMLPARS
MODULE=raptor
REQUIRES=xpcom raptor
CPPSRCS=nsDeque.cpp nsHTMLContentSink.cpp nsHTMLDelegate.cpp nsHTMLDTD.cpp \
CPPSRCS=nsHTMLContentSink.cpp nsHTMLDelegate.cpp nsHTMLDTD.cpp \
nsHTMLParser.cpp nsHTMLTokens.cpp nsParserNode.cpp nsScanner.cpp \
nsToken.cpp nsTokenizer.cpp nsDefaultTokenHandler.cpp
nsToken.cpp nsTokenizer.cpp nsTokenHandler.cpp \
CNavDTD.cpp CNavDelegate.cpp \
COtherDTD.cpp COtherDelegate.cpp
EXPORTS=nshtmlpars.h nsIContentSink.h nsIHTMLContentSink.h \
nsHTMLTokens.h nsIParserNode.h nsIParser.h nsToken.h
CPP_OBJS=.\$(OBJDIR)\nsDeque.obj .\$(OBJDIR)\nsHTMLContentSink.obj \
.\$(OBJDIR)\nsHTMLDelegate.obj .\$(OBJDIR)\nsHTMLParser.obj \
CPP_OBJS=.\$(OBJDIR)\nsHTMLContentSink.obj \
.\$(OBJDIR)\nsHTMLDelegate.obj .\$(OBJDIR)\nsHTMLParser.obj \
.\$(OBJDIR)\nsHTMLDTD.obj \
.\$(OBJDIR)\nsHTMLTokens.obj .\$(OBJDIR)\nsParserNode.obj \
.\$(OBJDIR)\nsScanner.obj .\$(OBJDIR)\nsToken.obj \
.\$(OBJDIR)\nsTokenizer.obj .\$(OBJDIR)\nsDefaultTokenHandler.obj
.\$(OBJDIR)\CNavDelegate.obj .\$(OBJDIR)\CNavDTD.obj \
.\$(OBJDIR)\COtherDelegate.obj .\$(OBJDIR)\COtherDTD.obj \
.\$(OBJDIR)\nsHTMLTokens.obj .\$(OBJDIR)\nsParserNode.obj \
.\$(OBJDIR)\nsScanner.obj .\$(OBJDIR)\nsToken.obj \
.\$(OBJDIR)\nsTokenizer.obj .\$(OBJDIR)\nsTokenHandler.obj
LINCS=-I$(XPDIST)\public\xpcom -I$(XPDIST)\public\raptor

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

@ -520,7 +520,7 @@ PRBool nsHTMLDTD::CanContainIndirect(PRInt32 aParent,PRInt32 aChild) const {
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
PRBool nsHTMLDTD::CanDisregard(PRInt32 aParent,PRInt32 aChild) const {
PRBool nsHTMLDTD::CanOmit(PRInt32 aParent,PRInt32 aChild) const {
PRBool result=PR_FALSE;
switch((eHTMLTags)aParent) {
@ -671,4 +671,19 @@ PRBool nsHTMLDTD::VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const {
return result;
}
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
PRInt32 nsHTMLDTD::CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const {
PRInt32 result=0;
return result;
}

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

@ -92,7 +92,7 @@ class nsHTMLDTD : public nsIDTD {
* @param aTag -- tag to test for containership
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool CanDisregard(PRInt32 aParent,PRInt32 aChild)const;
virtual PRBool CanOmit(PRInt32 aParent,PRInt32 aChild)const;
/** -------------------------------------------------------
* This method gets called to determine whether a given
@ -127,6 +127,19 @@ class nsHTMLDTD : public nsIDTD {
*/ //-----------------------------------------------------
virtual PRBool VerifyContextStack(eHTMLTags aStack[],PRInt32 aCount) const;
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
virtual PRInt32 CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const;
};

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

@ -43,6 +43,28 @@ CHTMLTokenizerDelegate::CHTMLTokenizerDelegate() :
ITokenizerDelegate(), mTokenDeque() {
}
/**-------------------------------------------------------
* Default constructor
*
* @updated gess 3/25/98
* @param
* @return
*-----------------------------------------------------*/
CHTMLTokenizerDelegate::CHTMLTokenizerDelegate(CHTMLTokenizerDelegate& aDelegate) :
ITokenizerDelegate(), mTokenDeque() {
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
eParseMode CHTMLTokenizerDelegate::GetParseMode() const {
return eParseMode_unknown;
}
/**-------------------------------------------------------
* This method is called just after a "<" has been consumed
* and we know we're at the start of some kind of tagged
@ -75,10 +97,10 @@ CToken* CHTMLTokenizerDelegate::ConsumeTag(PRUnichar aChar,CScanner& aScanner,PR
nsAutoString temp("<");
return ConsumeText(temp,aScanner,anErrorCode);
}
}
} //switch
if(result!=0) {
anErrorCode= result->Consume(aChar,&aScanner); //tell new token to finish consuming text...
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(anErrorCode) {
result=0;
delete result;
@ -103,7 +125,7 @@ void CHTMLTokenizerDelegate::ConsumeAttributes(PRUnichar aChar,CScanner& aScanne
while((!done) && (anErrorCode==kNoError)) {
CToken* result = new CAttributeToken(as);
if(result){
anErrorCode= result->Consume(aChar,&aScanner); //tell new token to finish consuming text...
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
mTokenDeque.Push(result);
}
aScanner.Peek(aChar);
@ -133,7 +155,7 @@ CToken* CHTMLTokenizerDelegate::ConsumeContentToEndTag(const nsString& aString,P
endTag.Append(aString);
endTag.Append(">");
CSkippedContentToken* sc=new CSkippedContentToken(endTag);
anErrorCode= sc->Consume(aChar,&aScanner); //tell new token to finish consuming text...
anErrorCode= sc->Consume(aChar,aScanner); //tell new token to finish consuming text...
return sc;
}
@ -150,10 +172,10 @@ CToken* CHTMLTokenizerDelegate::ConsumeContentToEndTag(const nsString& aString,P
CToken* CHTMLTokenizerDelegate::ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CStartToken* result=new CStartToken(nsAutoString(""));
if(result) {
anErrorCode= result->Consume(aChar,&aScanner); //tell new token to finish consuming text...
if(result->IsAttributed())
anErrorCode= result->Consume(aChar,aScanner); //tell new token to finish consuming text...
if(result->IsAttributed()) {
ConsumeAttributes(aChar,aScanner,anErrorCode);
}
//now that that's over with, we have one more problem to solve.
//In the case that we just read a <SCRIPT> or <STYLE> tags, we should go and
//consume all the content itself.
@ -176,8 +198,8 @@ CToken* CHTMLTokenizerDelegate::ConsumeStartTag(PRUnichar aChar,CScanner& aScann
CEndToken* endtoken=new CEndToken(str);
mTokenDeque.Push(endtoken);
}
}
} //if
} //if
}
return result;
}
@ -198,14 +220,13 @@ CToken* CHTMLTokenizerDelegate::ConsumeEntity(PRUnichar aChar,CScanner& aScanner
anErrorCode=aScanner.GetChar(ch);
if(nsString::IsAlpha(ch)) { //handle common enity references &xxx; or &#000.
result = new CEntityToken(nsAutoString(""));
anErrorCode= result->Consume(ch,&aScanner); //tell new token to finish consuming text...
anErrorCode= result->Consume(ch,aScanner); //tell new token to finish consuming text...
}
else if(kHashsign==ch) {
result = new CEntityToken(nsAutoString(""));
anErrorCode=result->Consume(ch,&aScanner);
anErrorCode=result->Consume(ch,aScanner);
}
else
{
else {
//oops, we're actually looking at plain text...
nsAutoString temp("&");
return ConsumeText(temp,aScanner,anErrorCode);
@ -226,7 +247,7 @@ CToken* CHTMLTokenizerDelegate::ConsumeEntity(PRUnichar aChar,CScanner& aScanner
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::ConsumeWhitespace(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode) {
CToken* result = new CWhitespaceToken(nsAutoString(""));
anErrorCode=result->Consume(aChar,&aScanner);
anErrorCode=result->Consume(aChar,aScanner);
return result;
}
#endif
@ -243,7 +264,7 @@ CToken* CHTMLTokenizerDelegate::ConsumeWhitespace(PRUnichar aChar,CScanner& aSca
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::ConsumeComment(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode){
CToken* result= new CCommentToken(nsAutoString(""));
anErrorCode=result->Consume(aChar,&aScanner);
anErrorCode=result->Consume(aChar,aScanner);
return result;
}
@ -259,9 +280,10 @@ CToken* CHTMLTokenizerDelegate::ConsumeComment(PRUnichar aChar,CScanner& aScanne
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::ConsumeText(const nsString& aString,CScanner& aScanner,PRInt32& anErrorCode){
CToken* result=new CTextToken(aString);
PRUnichar ch;
if(result)
anErrorCode=result->Consume(ch,&aScanner);
if(result) {
PRUnichar ch;
anErrorCode=result->Consume(ch,aScanner);
}
return result;
}
@ -277,8 +299,9 @@ CToken* CHTMLTokenizerDelegate::ConsumeText(const nsString& aString,CScanner& aS
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::ConsumeNewline(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode){
CToken* result=new CNewlineToken(nsAutoString(""));
if(result)
anErrorCode=result->Consume(aChar,&aScanner);
if(result) {
anErrorCode=result->Consume(aChar,aScanner);
}
return result;
}
#endif
@ -295,44 +318,54 @@ CToken* CHTMLTokenizerDelegate::ConsumeNewline(PRUnichar aChar,CScanner& aScanne
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::GetToken(CScanner* aScanner,PRInt32& anErrorCode){
CToken* CHTMLTokenizerDelegate::GetToken(CScanner& aScanner,PRInt32& anErrorCode){
CToken* result=0;
PRUnichar aChar;
if(mTokenDeque.GetSize()>0)
return mTokenDeque.Pop();
if(mTokenDeque.GetSize()>0) {
return (CToken*)mTokenDeque.Pop();
}
while(!aScanner->Eof())
{
anErrorCode=aScanner->GetChar(aChar);
while(!aScanner.Eof()) {
anErrorCode=aScanner.GetChar(aChar);
switch(aChar) {
case kAmpersand:
return ConsumeEntity(aChar,*aScanner,anErrorCode);
return ConsumeEntity(aChar,aScanner,anErrorCode);
case kLessThan:
return ConsumeTag(aChar,*aScanner,anErrorCode);
return ConsumeTag(aChar,aScanner,anErrorCode);
#ifdef TOKENIZE_CRLF
case kCR: case kLF:
return ConsumeNewline(aChar,*aScanner,anErrorCode);
return ConsumeNewline(aChar,aScanner,anErrorCode);
case kNotFound:
break;
#endif
default:
#ifdef TOKENIZE_WHITESPACE
if(nsString::IsSpace(aChar))
return ConsumeWhitespace(aChar,*aScanner,anErrorCode);
return ConsumeWhitespace(aChar,aScanner,anErrorCode);
else
#endif
{
nsAutoString temp(aChar);
return ConsumeText(temp,*aScanner,anErrorCode);
return ConsumeText(temp,aScanner,anErrorCode);
}
}
} //switch
if(anErrorCode==kEOF)
anErrorCode=0;
}
} //while
return result;
}
/*-------------------------------------------------------
*
* @update gess4/11/98
* @param
* @return
*------------------------------------------------------*/
CToken* CHTMLTokenizerDelegate::CreateTokenOfType(eHTMLTokenTypes aType) {
return 0;
}
/**-------------------------------------------------------
* This method is by the tokenizer, once for each new token
* we've constructed. This method determines whether or not

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

@ -43,40 +43,42 @@
#include "nsITokenizerDelegate.h"
#include "nsDeque.h"
#define MAXCOMMANDLEN (18)
class CHTMLTokenizerDelegate : public ITokenizerDelegate {
public:
CHTMLTokenizerDelegate();
CHTMLTokenizerDelegate();
CHTMLTokenizerDelegate(CHTMLTokenizerDelegate& aDelegate);
virtual CToken* GetToken(CScanner* aScanner,PRInt32& anErrorCode);
virtual PRBool WillAddToken(CToken& aToken);
virtual CToken* GetToken(CScanner& aScanner,PRInt32& anErrorCode);
virtual PRBool WillAddToken(CToken& aToken);
virtual PRBool WillTokenize();
virtual PRBool DidTokenize();
static void SelfTest();
virtual PRBool WillTokenize();
virtual PRBool DidTokenize();
virtual eParseMode GetParseMode() const;
static void SelfTest();
protected:
CToken* ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
void ConsumeAttributes(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeText(const nsString& aString,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* CreateTokenOfType(eHTMLTokenTypes aType);
CToken* ConsumeTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeStartTag(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
void ConsumeAttributes(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeText(const nsString& aString,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeEntity(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
#ifdef TOKENIZE_WHITESPACE
CToken* ConsumeWhitespace(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeWhitespace(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
#endif
CToken* ConsumeComment(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeComment(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
#ifdef TOKENIZE_CRLF
CToken* ConsumeNewline(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CToken* ConsumeNewline(PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
#endif
//the only special case method...
CToken* ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
virtual CToken* ConsumeContentToEndTag(const nsString& aString,PRUnichar aChar,CScanner& aScanner,PRInt32& anErrorCode);
CDeque mTokenDeque;
nsDeque mTokenDeque;
};

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

@ -17,21 +17,26 @@
*/
#include "nsHTMLParser.h"
#include "nsHTMLDelegate.h"
#include "nsHTMLContentSink.h"
#include "nsHTMLContentSink.h"
#include "nsTokenizer.h"
#include "nsHTMLTokens.h"
#include "nsString.h"
#include "nsIURL.h"
#include "nsDefaultTokenHandler.h"
#include "nsCRT.h"
#include "nsHTMLDTD.h"
#include "COtherDelegate.h"
#include "COtherDTD.h"
#include "CNavDelegate.h"
#include "CNavDTD.h"
static NS_DEFINE_IID(kISupportsIID, NS_ISUPPORTS_IID);
static NS_DEFINE_IID(kClassIID, NS_IHTML_PARSER_IID);
static NS_DEFINE_IID(kIParserIID, NS_IPARSER_IID);
static NS_DEFINE_IID(kIHTMLContentSinkIID, NS_IHTMLCONTENTSINK_IID);
static const char* kNullURL = "Error: Null URL given";
static const char* kNullTokenizer = "Error: Unable to construct tokenizer";
static const char* kNullToken = "Error: Null token given";
static const char* kInvalidTagStackPos = "Error: invalid tag stack position";
/**-------------------------------------------------------
@ -84,12 +89,13 @@ void nsHTMLParser::InitializeDefaultTokenHandlers() {
nsHTMLParser::nsHTMLParser() {
NS_INIT_REFCNT();
mSink=0;
mTokenHandlerCount=0;
mTagStackPos=0;
mContextStackPos=0;
mCurrentPos=0;
nsCRT::zero(mTagStack,sizeof(mTagStack));
mParseMode=eParseMode_unknown;
nsCRT::zero(mContextStack,sizeof(mContextStack));
nsCRT::zero(mTokenHandlers,sizeof(mTokenHandlers));
mDTD=new nsHTMLDTD();
mDTD=0;
mTokenHandlerCount=0;
InitializeDefaultTokenHandlers();
}
@ -102,13 +108,16 @@ nsHTMLParser::nsHTMLParser() {
* @return
*------------------------------------------------------*/
nsHTMLParser::~nsHTMLParser() {
DeleteTokenHandlers();
if(mCurrentPos)
delete mCurrentPos;
mCurrentPos=0;
if(mTokenizer)
delete mTokenizer;
if(mDTD)
delete mDTD;
mTokenizer=0;
mDTD=0;
NS_IF_RELEASE(mSink);
}
@ -160,8 +169,8 @@ nsresult nsHTMLParser::QueryInterface(const nsIID& aIID, void** aInstancePtr)
*------------------------------------------------------*/
eHTMLTags nsHTMLParser::NodeAt(PRInt32 aPos) const {
NS_PRECONDITION(0 <= aPos, "bad nodeAt");
if((aPos>-1) && (aPos<mTagStackPos))
return mTagStack[aPos];
if((aPos>-1) && (aPos<mContextStackPos))
return mContextStack[aPos];
return (eHTMLTags)kNotFound;
}
@ -174,8 +183,8 @@ eHTMLTags nsHTMLParser::NodeAt(PRInt32 aPos) const {
* @return
*------------------------------------------------------*/
eHTMLTags nsHTMLParser::GetTopNode() const {
if(mTagStackPos)
return mTagStack[mTagStackPos-1];
if(mContextStackPos)
return mContextStack[mContextStackPos-1];
return (eHTMLTags)kNotFound;
}
@ -188,8 +197,8 @@ eHTMLTags nsHTMLParser::GetTopNode() const {
* @return topmost index of tag on stack
*------------------------------------------------------*/
PRInt32 nsHTMLParser::GetTopmostIndex(eHTMLTags aTag) const {
for(int i=mTagStackPos-1;i>=0;i--){
if(mTagStack[i]==aTag)
for(int i=mContextStackPos-1;i>=0;i--){
if(mContextStack[i]==aTag)
return i;
}
return kNotFound;
@ -216,10 +225,9 @@ PRBool nsHTMLParser::IsOpen(eHTMLTags aTag) const {
* @return
*------------------------------------------------------*/
PRInt32 nsHTMLParser::GetStackPos() const {
return mTagStackPos;
return mContextStackPos;
}
/**-------------------------------------------------------
* Finds a tag handler for the given tag type, given in string.
*
@ -227,7 +235,22 @@ PRInt32 nsHTMLParser::GetStackPos() const {
* @param aString contains name of tag to be handled
* @return valid tag handler (if found) or null
*------------------------------------------------------*/
CDefaultTokenHandler* nsHTMLParser::GetTokenHandler(const nsString& aString) const{
nsHTMLParser& nsHTMLParser::DeleteTokenHandlers(void) {
for(int i=0;i<mTokenHandlerCount;i++){
delete mTokenHandlers[i];
}
mTokenHandlerCount=0;
return *this;
}
/**-------------------------------------------------------
* Finds a tag handler for the given tag type, given in string.
*
* @update gess 4/2/98
* @param aString contains name of tag to be handled
* @return valid tag handler (if found) or null
*------------------------------------------------------*/
CTokenHandler* nsHTMLParser::GetTokenHandler(const nsString& aString) const{
eHTMLTokenTypes theType=DetermineTokenType(aString);
return GetTokenHandler(theType);
}
@ -240,7 +263,7 @@ CDefaultTokenHandler* nsHTMLParser::GetTokenHandler(const nsString& aString) con
* @param aTagType type of tag to be handled
* @return valid tag handler (if found) or null
*------------------------------------------------------*/
CDefaultTokenHandler* nsHTMLParser::GetTokenHandler(eHTMLTokenTypes aType) const {
CTokenHandler* nsHTMLParser::GetTokenHandler(eHTMLTokenTypes aType) const {
for(int i=0;i<mTokenHandlerCount;i++) {
if(mTokenHandlers[i]->CanHandle(aType)) {
return mTokenHandlers[i];
@ -257,9 +280,14 @@ CDefaultTokenHandler* nsHTMLParser::GetTokenHandler(eHTMLTokenTypes aType) const
* @param
* @return
*------------------------------------------------------*/
CDefaultTokenHandler* nsHTMLParser::AddTokenHandler(CDefaultTokenHandler* aHandler) {
CTokenHandler* nsHTMLParser::AddTokenHandler(CTokenHandler* aHandler) {
NS_ASSERTION(0!=aHandler,"Error: Null handler argument");
if(aHandler) {
int max=sizeof(mTokenHandlers)/sizeof(mTokenHandlers[0]);
if(mTokenHandlerCount<max) {
mTokenHandlers[mTokenHandlerCount++]=aHandler;
}
}
return 0;
}
@ -272,20 +300,79 @@ CDefaultTokenHandler* nsHTMLParser::AddTokenHandler(CDefaultTokenHandler* aHandl
* @param nsIContentSink interface for node receiver
* @return
*------------------------------------------------------*/
void nsHTMLParser::SetContentSink(nsIContentSink* aSink) {
nsIContentSink* nsHTMLParser::SetContentSink(nsIContentSink* aSink) {
NS_PRECONDITION(0!=aSink,"sink cannot be null!");
nsIContentSink* old=mSink;
if(aSink) {
nsIHTMLContentSink* htmlSink;
if (NS_OK == aSink->QueryInterface(kIHTMLContentSinkIID, (void**)&htmlSink)) {
if ((nsHTMLContentSink*)(htmlSink) != mSink) {
NS_IF_RELEASE(mSink);
mSink = (nsHTMLContentSink*)(htmlSink);
}
else {
NS_RELEASE(htmlSink);
}
}
mSink=(nsHTMLContentSink*)(aSink);
}
return old;
}
/**-------------------------------------------------------
* This is where we loop over the tokens created in the
* tokenization phase, and try to make sense out of them.
*
* @update gess 3/25/98
* @param
* @return PR_TRUE if parse succeeded, PR_FALSE otherwise.
*------------------------------------------------------*/
PRBool nsHTMLParser::IterateTokens() {
nsDeque& deque=mTokenizer->GetDeque();
nsDequeIterator e=deque.End();
if(mCurrentPos)
delete mCurrentPos; //don't leak, now!
mCurrentPos=new nsDequeIterator(deque.Begin());
CToken* theToken;
PRBool done=PR_FALSE;
PRBool result=PR_TRUE;
PRInt32 iteration=0;
while((!done) && (result)) {
theToken=(CToken*)mCurrentPos->GetCurrent();
eHTMLTokenTypes type=eHTMLTokenTypes(theToken->GetTokenType());
iteration++; //debug purposes...
switch(eHTMLTokenTypes(type)){
case eToken_start:
result=HandleStartToken(theToken); break;
case eToken_end:
result=HandleEndToken(theToken); break;
case eToken_entity:
result=HandleEntityToken(theToken); break;
case eToken_text:
result=HandleTextToken(theToken); break;
case eToken_newline:
result=HandleNewlineToken(theToken); break;
case eToken_skippedcontent:
//used in cases like <SCRIPT> where we skip over script content.
result=HandleSkippedContentToken(theToken); break;
case eToken_attribute:
result=HandleAttributeToken(theToken); break;
case eToken_script:
result=HandleScriptToken(theToken); break;
case eToken_style:
result=HandleStyleToken(theToken); break;
case eToken_comment:
result=HandleCommentToken(theToken); break;
case eToken_whitespace:
result=HandleWhitespaceToken(theToken); break;
default:
//for all these non-interesting types, just skip them for now.
//later you have to Handle them, because they're relevent to certain containers (eg PRE).
break;
}
mDTD->VerifyContextStack(mContextStack,mContextStackPos);
++(*mCurrentPos);
done=PRBool(e==*mCurrentPos);
}
//One last thing...close any open containers.
if((PR_TRUE==result) && (mContextStackPos>0)) {
result=CloseContainersTo(0);
}
return result;
}
/**-------------------------------------------------------
@ -300,73 +387,53 @@ void nsHTMLParser::SetContentSink(nsIContentSink* aSink) {
* @return PR_TRUE if parse succeeded, PR_FALSE otherwise.
*------------------------------------------------------*/
PRBool nsHTMLParser::Parse(nsIURL* aURL){
NS_PRECONDITION(0!=aURL,"Error: URL cannot be null!");
return Parse(aURL,eParseMode_navigator);
}
/**-------------------------------------------------------
* This is the main controlling routine in the parsing process.
* Note that it may get called multiple times for the same scanner,
* since this is a pushed based system, and all the tokens may
* not have been consumed by the scanner during a given invocation
* of this method.
*
* @update gess 3/25/98
* @param aFilename -- const char* containing file to be parsed.
* @return PR_TRUE if parse succeeded, PR_FALSE otherwise.
*------------------------------------------------------*/
PRBool nsHTMLParser::Parse(nsIURL* aURL,eParseMode aMode){
NS_PRECONDITION(0!=aURL,kNullURL);
PRBool result=PR_FALSE;
if(aURL) {
result=PR_TRUE;
CHTMLTokenizerDelegate delegate;
mTokenizer=new CTokenizer(aURL, delegate);
mParseMode=aMode;
ITokenizerDelegate* theDelegate=0;
switch(mParseMode) {
case eParseMode_navigator:
theDelegate=new CNavDelegate();
mDTD= new CNavDTD();
break;
case eParseMode_other:
theDelegate=new COtherDelegate();
mDTD= new COtherDTD();
break;
default:
break;
}
if(!theDelegate) {
NS_ERROR(kNullTokenizer);
return PR_FALSE;
}
if(!mDTD) {
mDTD= new nsHTMLDTD();
}
mTokenizer=new CTokenizer(aURL, theDelegate, mParseMode);
mTokenizer->Tokenize();
//#define VERBOSE_DEBUG
#ifdef VERBOSE_DEBUG
mTokenizer->DebugDumpTokens(cout);
#endif
CDeque& deque=mTokenizer->GetDeque();
CDequeIterator e=deque.End();
if(mCurrentPos)
delete mCurrentPos; //don't leak, now!
mCurrentPos=new CDequeIterator(deque.Begin());
CToken* theToken;
PRBool done=PR_FALSE;
PRInt32 iteration=0;
while((!done) && (result)) {
theToken=*mCurrentPos;
eHTMLTokenTypes type=eHTMLTokenTypes(theToken->GetTokenType());
iteration++; //debug purposes...
switch(eHTMLTokenTypes(type)){
case eToken_start:
result=HandleStartToken(theToken); break;
case eToken_end:
result=HandleEndToken(theToken); break;
case eToken_entity:
result=HandleEntityToken(theToken); break;
case eToken_text:
result=HandleTextToken(theToken); break;
case eToken_newline:
result=HandleNewlineToken(theToken); break;
case eToken_skippedcontent:
//used in cases like <SCRIPT> where we skip over script content.
result=HandleSkippedContentToken(theToken); break;
case eToken_attribute:
result=HandleAttributeToken(theToken); break;
case eToken_script:
result=HandleScriptToken(theToken); break;
case eToken_style:
result=HandleStyleToken(theToken); break;
case eToken_comment:
result=HandleCommentToken(theToken); break;
case eToken_whitespace:
result=HandleWhitespaceToken(theToken); break;
default:
//for all these non-interesting types, just skip them for now.
//later you have to Handle them, because they're relevent to certain containers (eg PRE).
break;
}
mDTD->VerifyContextStack(mTagStack,mTagStackPos);
done=PRBool(++(*mCurrentPos)==e);
}
//One last thing...close any open containers.
if((PR_TRUE==result) && (mTagStackPos>0)) {
result=CloseContainersTo(0);
}
result=IterateTokens();
}
return result;
}
@ -383,7 +450,7 @@ PRBool nsHTMLParser::Parse(nsIURL* aURL){
* @return PR_TRUE if parsing concluded successfully.
*------------------------------------------------------*/
PRBool nsHTMLParser::ResumeParse() {
PRBool result=PR_TRUE;
PRBool result=IterateTokens();
return result;
}
@ -396,8 +463,8 @@ PRBool nsHTMLParser::ResumeParse() {
*------------------------------------------------------*/
PRInt32 nsHTMLParser::CollectAttributes(nsCParserNode& aNode){
eHTMLTokenTypes subtype=eToken_attribute;
CDeque& deque=mTokenizer->GetDeque();
CDequeIterator end=deque.End();
nsDeque& deque=mTokenizer->GetDeque();
nsDequeIterator end=deque.End();
while((*mCurrentPos!=end) && (eToken_attribute==subtype)) {
CHTMLToken* tkn=(CHTMLToken*)(++(*mCurrentPos));
@ -418,8 +485,8 @@ PRInt32 nsHTMLParser::CollectAttributes(nsCParserNode& aNode){
*------------------------------------------------------*/
PRInt32 nsHTMLParser::CollectSkippedContent(nsCParserNode& aNode){
eHTMLTokenTypes subtype=eToken_attribute;
CDeque& deque=mTokenizer->GetDeque();
CDequeIterator end=deque.End();
nsDeque& deque=mTokenizer->GetDeque();
nsDequeIterator end=deque.End();
PRInt32 count=0;
while((*mCurrentPos!=end) && (eToken_attribute==subtype)) {
@ -450,7 +517,7 @@ PRInt32 nsHTMLParser::CollectSkippedContent(nsCParserNode& aNode){
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleStartToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_FALSE;
CStartToken* st= (CStartToken*)(aToken);
@ -551,7 +618,7 @@ PRBool nsHTMLParser::HandleStartToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleEndToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_FALSE;
CEndToken* st = (CEndToken*)(aToken);
@ -605,7 +672,7 @@ PRBool nsHTMLParser::HandleEndToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleEntityToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
CEntityToken* et = (CEntityToken*)(aToken);
PRBool result=PR_TRUE;
nsCParserNode aNode((CHTMLToken*)aToken);
@ -624,6 +691,7 @@ PRBool nsHTMLParser::HandleEntityToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleCommentToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,kNullToken);
return PR_TRUE;
}
@ -638,11 +706,13 @@ PRBool nsHTMLParser::HandleCommentToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleWhitespaceToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_TRUE;
if(PR_TRUE==IsWithinBody()) {
//now we know we're in the body <i>somewhere</i>.
//let's see if the current tag can contain a ws.
result=mDTD->CanDisregard(mTagStack[mTagStackPos-1],eHTMLTag_whitespace);
result=mDTD->CanOmit(mContextStack[mContextStackPos-1],eHTMLTag_whitespace);
if(PR_FALSE==result)
result=HandleTextToken(aToken);
}
@ -660,11 +730,13 @@ PRBool nsHTMLParser::HandleWhitespaceToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleNewlineToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_TRUE;
if(PR_TRUE==IsWithinBody()) {
//now we know we're in the body <i>somewhere</i>.
//let's see if the current tag can contain a ws.
result=mDTD->CanDisregard(mTagStack[mTagStackPos-1],eHTMLTag_newline);
result=mDTD->CanOmit(mContextStack[mContextStackPos-1],eHTMLTag_newline);
if(PR_FALSE==result)
result=HandleTextToken(aToken);
}
@ -682,7 +754,8 @@ PRBool nsHTMLParser::HandleNewlineToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleTextToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_TRUE;
nsCParserNode aNode((CHTMLToken*)aToken);
result=AddLeaf(aNode);
@ -700,7 +773,8 @@ PRBool nsHTMLParser::HandleTextToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleSkippedContentToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
PRBool result=PR_TRUE;
if(IsWithinBody()) {
@ -721,7 +795,7 @@ PRBool nsHTMLParser::HandleSkippedContentToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleAttributeToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
NS_ERROR("attribute encountered -- this shouldn't happen!");
CAttributeToken* at = (CAttributeToken*)(aToken);
@ -738,7 +812,7 @@ PRBool nsHTMLParser::HandleAttributeToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleScriptToken(CToken* aToken) {
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
CScriptToken* st = (CScriptToken*)(aToken);
PRBool result=PR_TRUE;
@ -754,7 +828,7 @@ PRBool nsHTMLParser::HandleScriptToken(CToken* aToken) {
* @return PR_TRUE if all went well; PR_FALSE if error occured
*------------------------------------------------------*/
PRBool nsHTMLParser::HandleStyleToken(CToken* aToken){
NS_PRECONDITION(0!=aToken,"token cannot be null!");
NS_PRECONDITION(0!=aToken,kNullToken);
CStyleToken* st = (CStyleToken*)(aToken);
PRBool result=PR_TRUE;
@ -770,8 +844,8 @@ PRBool nsHTMLParser::HandleStyleToken(CToken* aToken){
* @return PR_TRUE if given tag can contain other tags
*------------------------------------------------------*/
PRBool nsHTMLParser::IsWithinBody(void) const {
for(int i=0;i<mTagStackPos;i++) {
if(eHTMLTag_body==mTagStack[i])
for(int i=0;i<mContextStackPos;i++) {
if(eHTMLTag_body==mContextStack[i])
return PR_TRUE;
}
return PR_FALSE;
@ -787,9 +861,10 @@ PRBool nsHTMLParser::IsWithinBody(void) const {
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenHTML(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=mSink->OpenHTML(aNode);
mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
mContextStack[mContextStackPos++]=(eHTMLTags)aNode.GetNodeType();
return result;
}
@ -803,9 +878,9 @@ PRBool nsHTMLParser::OpenHTML(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseHTML(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRBool result=mSink->CloseHTML(aNode);
mTagStack[--mTagStackPos]=eHTMLTag_unknown;
mContextStack[--mContextStackPos]=eHTMLTag_unknown;
return result;
}
@ -819,9 +894,7 @@ PRBool nsHTMLParser::CloseHTML(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenHead(const nsIParserNode& aNode){
// NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
PRBool result=mSink->OpenHead(aNode);
// mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
return result;
}
@ -834,9 +907,7 @@ PRBool nsHTMLParser::OpenHead(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseHead(const nsIParserNode& aNode){
// NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
PRBool result=mSink->CloseHead(aNode);
// mTagStack[--mTagStackPos]=eHTMLTag_unknown;
return result;
}
@ -849,7 +920,7 @@ PRBool nsHTMLParser::CloseHead(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenBody(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=PR_TRUE;
eHTMLTags topTag=(eHTMLTags)nsHTMLParser::GetTopNode();
@ -882,7 +953,7 @@ PRBool nsHTMLParser::OpenBody(const nsIParserNode& aNode){
if(PR_TRUE==result) {
result=mSink->OpenBody(aNode);
mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
mContextStack[mContextStackPos++]=(eHTMLTags)aNode.GetNodeType();
}
return result;
}
@ -896,9 +967,9 @@ PRBool nsHTMLParser::OpenBody(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseBody(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=mSink->CloseBody(aNode);
mTagStack[--mTagStackPos]=eHTMLTag_unknown;
mContextStack[--mContextStackPos]=eHTMLTag_unknown;
return result;
}
@ -911,9 +982,9 @@ PRBool nsHTMLParser::CloseBody(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenForm(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=mSink->OpenForm(aNode);
mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
mContextStack[mContextStackPos++]=(eHTMLTags)aNode.GetNodeType();
return result;
}
@ -926,9 +997,9 @@ PRBool nsHTMLParser::OpenForm(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseForm(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRBool result=mSink->CloseContainer(aNode);
mTagStack[--mTagStackPos]=eHTMLTag_unknown;
mContextStack[--mContextStackPos]=eHTMLTag_unknown;
return result;
}
@ -941,9 +1012,9 @@ PRBool nsHTMLParser::CloseForm(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenFrameset(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=mSink->OpenFrameset(aNode);
mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
mContextStack[mContextStackPos++]=(eHTMLTags)aNode.GetNodeType();
return result;
}
@ -956,9 +1027,9 @@ PRBool nsHTMLParser::OpenFrameset(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseFrameset(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRBool result=mSink->CloseFrameset(aNode);
mTagStack[--mTagStackPos]=eHTMLTag_unknown;
mContextStack[--mContextStackPos]=eHTMLTag_unknown;
return result;
}
@ -971,9 +1042,9 @@ PRBool nsHTMLParser::CloseFrameset(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::OpenContainer(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos >= 0, kInvalidTagStackPos);
PRBool result=mSink->OpenContainer(aNode);
mTagStack[mTagStackPos++]=(eHTMLTags)aNode.GetNodeType();
mContextStack[mContextStackPos++]=(eHTMLTags)aNode.GetNodeType();
return result;
}
@ -986,7 +1057,7 @@ PRBool nsHTMLParser::OpenContainer(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseContainer(const nsIParserNode& aNode){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRBool result=PR_FALSE;
//XXX Hack! We know this is wrong, but it works
@ -1010,7 +1081,7 @@ PRBool nsHTMLParser::CloseContainer(const nsIParserNode& aNode){
case eHTMLTag_title:
default:
result=mSink->CloseContainer(aNode);
mTagStack[--mTagStackPos]=eHTMLTag_unknown;
mContextStack[--mContextStackPos]=eHTMLTag_unknown;
break;
}
return result;
@ -1025,16 +1096,16 @@ PRBool nsHTMLParser::CloseContainer(const nsIParserNode& aNode){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseContainersTo(PRInt32 anIndex){
NS_PRECONDITION(mTagStackPos >= 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRBool result=PR_TRUE;
nsAutoString empty;
CHTMLToken aToken(empty);
nsCParserNode theNode(&aToken);
if((anIndex<mTagStackPos) && (anIndex>=0)) {
while(mTagStackPos>anIndex) {
aToken.SetHTMLTag(mTagStack[mTagStackPos-1]);
if((anIndex<mContextStackPos) && (anIndex>=0)) {
while(mContextStackPos>anIndex) {
aToken.SetHTMLTag(mContextStack[mContextStackPos-1]);
result=CloseContainer(theNode);
}
}
@ -1050,7 +1121,7 @@ PRBool nsHTMLParser::CloseContainersTo(PRInt32 anIndex){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseContainersTo(eHTMLTags aTag){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
PRInt32 pos=GetTopmostIndex(aTag);
PRBool result=PR_FALSE;
@ -1082,11 +1153,11 @@ PRBool nsHTMLParser::CloseContainersTo(eHTMLTags aTag){
* @return TRUE if ok, FALSE if error
*------------------------------------------------------*/
PRBool nsHTMLParser::CloseTopmostContainer(){
NS_PRECONDITION(mTagStackPos > 0, "invalid tag stack pos");
NS_PRECONDITION(mContextStackPos > 0, kInvalidTagStackPos);
nsAutoString empty;
CEndToken aToken(empty);
aToken.SetHTMLTag(mTagStack[mTagStackPos-1]);
aToken.SetHTMLTag(mContextStack[mContextStackPos-1]);
nsCParserNode theNode(&aToken);
return CloseContainer(theNode);
@ -1132,8 +1203,8 @@ PRBool nsHTMLParser::CreateContextStackFor(PRInt32 aChildTag){
//now, compare requested stack against existing stack...
PRInt32 pos=0;
while(pos<mTagStackPos) {
if(mTagStack[pos]==tags[tagCount-1-pos]) {
while(pos<mContextStackPos) {
if(mContextStack[pos]==tags[tagCount-1-pos]) {
pos++;
}
else {

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

@ -59,7 +59,8 @@
#include "nsDeque.h"
#include "nsHTMLTokens.h"
#include "nsParserNode.h"
#include "nsDefaultTokenHandler.h"
#include "nsTokenHandler.h"
#include "nsParserTypes.h"
#define NS_IHTML_PARSER_IID \
@ -77,13 +78,14 @@ class nsHTMLDTD;
class nsHTMLParser : public nsIParser {
public:
friend class CDefaultTokenHandler;
friend class CTokenHandler;
NS_DECL_ISUPPORTS
nsHTMLParser();
~nsHTMLParser();
virtual void SetContentSink(nsIContentSink* aSink);
virtual nsIContentSink* SetContentSink(nsIContentSink* aSink);
virtual PRBool Parse(nsIURL* aURL);
virtual PRBool Parse(nsIURL* aURL,eParseMode aMode);
virtual PRBool ResumeParse();
@ -102,6 +104,7 @@ friend class CDefaultTokenHandler;
PRBool IsWithinBody(void) const;
protected:
PRBool IterateTokens();
eHTMLTags NodeAt(PRInt32 aPos) const;
eHTMLTags GetTopNode() const;
PRInt32 GetStackPos() const;
@ -109,9 +112,10 @@ friend class CDefaultTokenHandler;
PRInt32 CollectAttributes(nsCParserNode& aNode);
PRInt32 CollectSkippedContent(nsCParserNode& aNode);
void InitializeDefaultTokenHandlers();
CDefaultTokenHandler* GetTokenHandler(const nsString& aString) const;
CDefaultTokenHandler* GetTokenHandler(eHTMLTokenTypes aType) const;
CDefaultTokenHandler* AddTokenHandler(CDefaultTokenHandler* aHandler);
CTokenHandler* GetTokenHandler(const nsString& aString) const;
CTokenHandler* GetTokenHandler(eHTMLTokenTypes aType) const;
CTokenHandler* AddTokenHandler(CTokenHandler* aHandler);
nsHTMLParser& DeleteTokenHandlers(void);
protected:
@ -142,14 +146,15 @@ friend class CDefaultTokenHandler;
nsIHTMLContentSink* mSink;
CTokenizer* mTokenizer;
eHTMLTags mTagStack[50];
PRInt32 mTagStackPos;
eHTMLTags mContextStack[50];
PRInt32 mContextStackPos;
CDefaultTokenHandler* mTokenHandlers[100];
PRInt32 mTokenHandlerCount;
CDequeIterator* mCurrentPos;
CTokenHandler* mTokenHandlers[100];
PRInt32 mTokenHandlerCount;
nsDequeIterator* mCurrentPos;
nsHTMLDTD* mDTD;
eParseMode mParseMode;
};

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

@ -355,27 +355,25 @@ PRBool CStartToken::IsAttributed(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CStartToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CStartToken::Consume(PRUnichar aChar, CScanner& aScanner) {
//if you're here, we've already Consumed the < char, and are
//ready to Consume the rest of the open tag identifier.
//Stop consuming as soon as you see a space or a '>'.
//NOTE: We don't Consume the tag attributes here, nor do we eat the ">"
PRInt32 result=kNoError;
mTextValue=aChar;
result=aScanner->ReadWhile(mTextValue,gIdentChars,PR_FALSE);
PRInt32 result=aScanner.ReadWhile(mTextValue,gIdentChars,PR_FALSE);
//Good. Now, let's skip whitespace after the identifier,
//and see if the next char is ">". If so, we have a complete
//tag without attributes.
aScanner->SkipWhite();
result=aScanner->GetChar(aChar);
aScanner.SkipWhite();
result=aScanner.GetChar(aChar);
if(kGreaterThan!=aChar) { //look for '>'
//push that char back, since we apparently have attributes...
aScanner->PutBack(aChar);
aScanner.PutBack(aChar);
mAttributed=PR_TRUE;
}
return result;
@ -417,21 +415,17 @@ CEndToken::CEndToken(const nsString& aName) : CHTMLToken(aName) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CEndToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CEndToken::Consume(PRUnichar aChar, CScanner& aScanner) {
//if you're here, we've already Consumed the <! chars, and are
//ready to Consume the rest of the open tag identifier.
//Stop consuming as soon as you see a space or a '>'.
//NOTE: We don't Consume the tag attributes here, nor do we eat the ">"
PRInt32 result=kNotFound;
if(aScanner) {
mTextValue="";
static nsAutoString terminals(">");
result=aScanner->ReadUntil(mTextValue,terminals,PR_FALSE);
aScanner->GetChar(aChar); //eat the closing '>;
}
mTextValue="";
static nsAutoString terminals(">");
PRInt32 result=aScanner.ReadUntil(mTextValue,terminals,PR_FALSE);
aScanner.GetChar(aChar); //eat the closing '>;
return result;
};
@ -528,21 +522,17 @@ PRInt32 CTextToken::GetTokenType(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CTextToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CTextToken::Consume(PRUnichar aChar, CScanner& aScanner) {
PRInt32 result=kNotFound;
if(aScanner) {
#ifdef TOKENIZE_CRLF
static nsAutoString terminals("&<\r\n");
#else
static nsAutoString terminals("&<");
#endif
result=aScanner->ReadUntil(mTextValue,terminals,PR_FALSE);
PRInt32 result=aScanner.ReadUntil(mTextValue,terminals,PR_FALSE);
#ifndef TOKENIZE_CRLF
mTextValue.StripChars("\r");
#endif
}
return result;
};
@ -567,37 +557,31 @@ CCommentToken::CCommentToken(const nsString& aName) : CHTMLToken(aName) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CCommentToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CCommentToken::Consume(PRUnichar aChar, CScanner& aScanner) {
PRInt32 result=kNotFound;
PRUnichar ch,ch2;
static nsAutoString terminals(">");
if(aScanner) {
aScanner->GetChar(ch);
result=aScanner->GetChar(ch);
mTextValue="<!";
if(kMinus==ch) {
aScanner->GetChar(ch2);
if(kMinus==ch2) {
//in this case, we're reading a long-form comment <-- xxx -->
mTextValue+="--";
PRInt32 findpos=-1;
while((findpos==kNotFound) && (!result)) {
result=aScanner->ReadUntil(mTextValue,terminals,PR_TRUE);
findpos=mTextValue.RFind("-->");
}
return result;
aScanner.GetChar(ch);
PRInt32 result=aScanner.GetChar(ch);
mTextValue="<!";
if(kMinus==ch) {
aScanner.GetChar(ch2);
if(kMinus==ch2) {
//in this case, we're reading a long-form comment <-- xxx -->
mTextValue+="--";
PRInt32 findpos=-1;
while((findpos==kNotFound) && (!result)) {
result=aScanner.ReadUntil(mTextValue,terminals,PR_TRUE);
findpos=mTextValue.RFind("-->");
}
return result;
}
//if you're here, we're consuming a "short-form" comment
mTextValue+=ch;
result=aScanner->ReadUntil(mTextValue,terminals,PR_TRUE);
}
//if you're here, we're consuming a "short-form" comment
mTextValue+=ch;
result=aScanner.ReadUntil(mTextValue,terminals,PR_TRUE);
return result;
};
@ -665,16 +649,11 @@ PRInt32 CNewlineToken::GetTokenType(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CNewlineToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 result=kNotFound;
if(aScanner) {
mTextValue=aChar;
static nsAutoString crlfChars("\r\n");
result=aScanner->ReadWhile(mTextValue,crlfChars,PR_FALSE);
mTextValue.StripChars("\r");
}
PRInt32 CNewlineToken::Consume(PRUnichar aChar, CScanner& aScanner) {
mTextValue=aChar;
static nsAutoString crlfChars("\r\n");
PRInt32 result=aScanner.ReadWhile(mTextValue,crlfChars,PR_FALSE);
mTextValue.StripChars("\r");
return result;
};
#endif /* TOKENIZE_CRLF */
@ -739,27 +718,24 @@ void CAttributeToken::DebugDumpToken(ostream& out) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 ConsumeQuotedString(PRUnichar aChar,nsString& aString,CScanner* aScanner){
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 ConsumeQuotedString(PRUnichar aChar,nsString& aString,CScanner& aScanner){
static nsAutoString terminals1(">'");
static nsAutoString terminals2(">\"");
PRInt32 result=kNotFound;
if(aScanner) {
switch(aChar) {
case kQuote:
result=aScanner->ReadUntil(aString,terminals2,PR_TRUE);
break;
case kApostrophe:
result=aScanner->ReadUntil(aString,terminals1,PR_TRUE);
break;
default:
break;
}
PRUnichar ch=aString.Last();
if(ch!=aChar)
aString+=aChar;
switch(aChar) {
case kQuote:
result=aScanner.ReadUntil(aString,terminals2,PR_TRUE);
break;
case kApostrophe:
result=aScanner.ReadUntil(aString,terminals1,PR_TRUE);
break;
default:
break;
}
PRUnichar ch=aString.Last();
if(ch!=aChar)
aString+=aChar;
return result;
}
@ -772,14 +748,11 @@ PRInt32 ConsumeQuotedString(PRUnichar aChar,nsString& aString,CScanner* aScanner
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 ConsumeAttributeValueText(PRUnichar aChar,nsString& aString,CScanner* aScanner){
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 ConsumeAttributeValueText(PRUnichar aChar,nsString& aString,CScanner& aScanner){
PRInt32 result=kNotFound;
if(aScanner){
static nsAutoString terminals(" \t\b\r\n>");
result=aScanner->ReadUntil(aString,terminals,PR_FALSE);
}
static nsAutoString terminals(" \t\b\r\n>");
result=aScanner.ReadUntil(aString,terminals,PR_FALSE);
return result;
}
@ -792,55 +765,51 @@ PRInt32 ConsumeAttributeValueText(PRUnichar aChar,nsString& aString,CScanner* aS
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CAttributeToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CAttributeToken::Consume(PRUnichar aChar, CScanner& aScanner) {
PRInt32 result=kNotFound;
if(aScanner) {
aScanner->SkipWhite(); //skip leading whitespace
result=aScanner->Peek(aChar);
if(kEOF!=result) {
if(kQuote==aChar) { //if you're here, handle quoted key...
aScanner->GetChar(aChar); //skip the quote sign...
mTextKey=aChar;
result=ConsumeQuotedString(aChar,mTextKey,aScanner);
}
else if(kHashsign==aChar) {
aScanner->GetChar(aChar); //skip the hash sign...
mTextKey=aChar;
result=aScanner->ReadWhile(mTextKey,gDigits,PR_TRUE);
}
else {
//If you're here, handle an unquoted key.
//Don't forget to reduce entities inline!
static nsAutoString terminals(" >=\t\b\r\n\"");
result=aScanner->ReadUntil(mTextKey,terminals,PR_FALSE);
}
aScanner.SkipWhite(); //skip leading whitespace
PRInt32 result=aScanner.Peek(aChar);
if(kEOF!=result) {
if(kQuote==aChar) { //if you're here, handle quoted key...
aScanner.GetChar(aChar); //skip the quote sign...
mTextKey=aChar;
result=ConsumeQuotedString(aChar,mTextKey,aScanner);
}
else if(kHashsign==aChar) {
aScanner.GetChar(aChar); //skip the hash sign...
mTextKey=aChar;
result=aScanner.ReadWhile(mTextKey,gDigits,PR_TRUE);
}
else {
//If you're here, handle an unquoted key.
//Don't forget to reduce entities inline!
static nsAutoString terminals(" >=\t\b\r\n\"");
result=aScanner.ReadUntil(mTextKey,terminals,PR_FALSE);
}
//now it's time to Consume the (optional) value...
if(!(result=aScanner->SkipWhite())) {
if(!(result=aScanner->Peek(aChar))) {
if(kEqual==aChar){
aScanner->GetChar(aChar); //skip the equal sign...
aScanner->SkipWhite(); //now skip any intervening whitespace
aScanner->GetChar(aChar); //and grab the next char.
if((kQuote==aChar) || (kApostrophe==aChar)) {
mTextValue=aChar;
result=ConsumeQuotedString(aChar,mTextValue,aScanner);
}
else {
mTextValue=aChar; //it's an alphanum attribute...
result=ConsumeAttributeValueText(aChar,mTextValue,aScanner);
}
aScanner->SkipWhite();
//now it's time to Consume the (optional) value...
if(!(result=aScanner.SkipWhite())) {
if(!(result=aScanner.Peek(aChar))) {
if(kEqual==aChar){
aScanner.GetChar(aChar); //skip the equal sign...
aScanner.SkipWhite(); //now skip any intervening whitespace
aScanner.GetChar(aChar); //and grab the next char.
if((kQuote==aChar) || (kApostrophe==aChar)) {
mTextValue=aChar;
result=ConsumeQuotedString(aChar,mTextValue,aScanner);
}
else {
mTextValue=aChar; //it's an alphanum attribute...
result=ConsumeAttributeValueText(aChar,mTextValue,aScanner);
}
aScanner.SkipWhite();
}
}
aScanner->Peek(aChar);
mLastAttribute= PRBool((kGreaterThan==aChar) || (kEOF==result));
}
aScanner.Peek(aChar);
mLastAttribute= PRBool((kGreaterThan==aChar) || (kEOF==result));
}
return result;
};
@ -908,15 +877,11 @@ PRInt32 CWhitespaceToken::GetTokenType(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CWhitespaceToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CWhitespaceToken::Consume(PRUnichar aChar, CScanner& aScanner) {
PRInt32 result=kNotFound;
if(aScanner) {
mTextValue=aChar;
aScanner->ReadWhile(mTextValue,gWhitespace,PR_FALSE);
mTextValue.StripChars("\r");
}
mTextValue=aChar;
PRInt32 result=aScanner.ReadWhile(mTextValue,gWhitespace,PR_FALSE);
mTextValue.StripChars("\r");
return result;
};
#endif /* TOKENIZE_WHITESPACE */
@ -931,8 +896,9 @@ PRInt32 CWhitespaceToken::Consume(PRUnichar aChar, CScanner* aScanner) {
CEntityToken::CEntityToken(const nsString& aName) : CHTMLToken(aName) {
mOrdinalValue=eToken_entity;
#ifdef VERBOSE_DEBUG
if(!VerifyEntityTable())
if(!VerifyEntityTable()) {
cout<<"Entity table is invalid!" << endl;
}
#endif
}
@ -944,14 +910,10 @@ CEntityToken::CEntityToken(const nsString& aName) : CHTMLToken(aName) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CEntityToken::Consume(PRUnichar aChar, CScanner* aScanner) {
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CEntityToken::Consume(PRUnichar aChar, CScanner& aScanner) {
PRInt32 result=kNotFound;
if(aScanner) {
mTextValue=aChar;
result=ConsumeEntity(aChar,mTextValue,aScanner);
}
mTextValue=aChar;
PRInt32 result=ConsumeEntity(aChar,mTextValue,aScanner);
return result;
};
@ -987,30 +949,27 @@ PRInt32 CEntityToken::GetTokenType(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CEntityToken::ConsumeEntity(PRUnichar aChar,nsString& aString,CScanner* aScanner){
NS_PRECONDITION(0!=aScanner,kNullScanner);
PRInt32 CEntityToken::ConsumeEntity(PRUnichar aChar,nsString& aString,CScanner& aScanner){
PRInt32 result=kNotFound;
if(aScanner) {
aScanner->Peek(aChar);
if(kLeftBrace==aChar) {
//you're consuming a script entity...
static nsAutoString terminals("}>");
result=aScanner->ReadUntil(aString,terminals,PR_FALSE);
aScanner->Peek(aChar);
if(kRightBrace==aChar) {
aString+=kRightBrace; //append rightbrace, and...
aScanner->GetChar(aChar);//yank the closing right-brace
}
aScanner.Peek(aChar);
if(kLeftBrace==aChar) {
//you're consuming a script entity...
static nsAutoString terminals("}>");
result=aScanner.ReadUntil(aString,terminals,PR_FALSE);
aScanner.Peek(aChar);
if(kRightBrace==aChar) {
aString+=kRightBrace; //append rightbrace, and...
aScanner.GetChar(aChar);//yank the closing right-brace
}
else
{
result=aScanner->ReadWhile(aString,gIdentChars,PR_FALSE);
aScanner->Peek(aChar);
if (kSemicolon == aChar) {
// consume semicolon that stopped the scan
aScanner->GetChar(aChar);
}
}
else
{
result=aScanner.ReadWhile(aString,gIdentChars,PR_FALSE);
aScanner.Peek(aChar);
if (kSemicolon == aChar) {
// consume semicolon that stopped the scan
aScanner.GetChar(aChar);
}
}
return result;
@ -1236,14 +1195,14 @@ PRInt32 CSkippedContentToken::GetTokenType(void) {
* @param aScanner -- controller of underlying input source
* @return error result
*------------------------------------------------------*/
PRInt32 CSkippedContentToken::Consume(PRUnichar aChar,CScanner* aScanner) {
PRInt32 CSkippedContentToken::Consume(PRUnichar aChar,CScanner& aScanner) {
PRBool done=PR_FALSE;
PRInt32 result=kNoError;
nsString temp;
while((!done) && (!aScanner->Eof())) {
while((!done) && (!aScanner.Eof())) {
static nsAutoString terminals(">");
result=aScanner->ReadUntil(temp,terminals,PR_TRUE);
result=aScanner.ReadUntil(temp,terminals,PR_TRUE);
done=PRBool(kNotFound!=temp.RFind(mTextValue,PR_TRUE));
}
mTextValue=temp;

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

@ -106,8 +106,8 @@ enum eHTMLAttributes {
eHTMLAttr_title, eHTMLAttr_wordbreak, eHTMLAttr_width, eHTMLAttr_xmp
};
PRInt32 ConsumeQuotedString(PRUnichar aChar,nsString& aString,CScanner* aScanner);
PRInt32 ConsumeAttributeText(PRUnichar aChar,nsString& aString,CScanner* aScanner);
PRInt32 ConsumeQuotedString(PRUnichar aChar,nsString& aString,CScanner& aScanner);
PRInt32 ConsumeAttributeText(PRUnichar aChar,nsString& aString,CScanner& aScanner);
PRInt32 FindEntityIndex(const char* aBuffer,PRInt32 aBufLen=-1);
eHTMLTags DetermineHTMLTagType(const nsString& aString);
eHTMLTokenTypes DetermineTokenType(const nsString& aString);
@ -139,7 +139,7 @@ protected:
class CStartToken: public CHTMLToken {
public:
CStartToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual eHTMLTags GetHTMLTag();
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
@ -163,7 +163,7 @@ class CStartToken: public CHTMLToken {
class CEndToken: public CHTMLToken {
public:
CEndToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual eHTMLTags GetHTMLTag();
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
@ -182,7 +182,7 @@ class CEndToken: public CHTMLToken {
class CCommentToken: public CHTMLToken {
public:
CCommentToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
char mLeadingChar;
@ -202,8 +202,8 @@ class CEntityToken : public CHTMLToken {
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
PRInt32 TranslateToUnicodeStr(nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
static PRInt32 ConsumeEntity(PRUnichar aChar,nsString& aString,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
static PRInt32 ConsumeEntity(PRUnichar aChar,nsString& aString,CScanner& aScanner);
static PRInt32 TranslateToUnicodeStr(PRInt32 aValue,nsString& aString);
static PRInt32 FindEntityIndex(const char* aBuffer,PRInt32 aBufLen=-1);
static PRBool VerifyEntityTable(void);
@ -226,7 +226,7 @@ class CEntityToken : public CHTMLToken {
class CWhitespaceToken: public CHTMLToken {
public:
CWhitespaceToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
};
@ -242,7 +242,7 @@ class CWhitespaceToken: public CHTMLToken {
class CTextToken: public CHTMLToken {
public:
CTextToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
};
@ -259,7 +259,7 @@ class CTextToken: public CHTMLToken {
class CAttributeToken: public CHTMLToken {
public:
CAttributeToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
virtual nsString& GetKey(void) {return mTextKey;}
@ -282,7 +282,7 @@ class CAttributeToken: public CHTMLToken {
class CNewlineToken: public CHTMLToken {
public:
CNewlineToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
};
@ -334,7 +334,7 @@ class CStyleToken: public CHTMLToken {
class CSkippedContentToken: public CAttributeToken {
public:
CSkippedContentToken(const nsString& aString);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual const char* GetClassName(void);
virtual PRInt32 GetTokenType(void);
protected:

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

@ -77,10 +77,11 @@ class nsIDTD : public nsISupports {
* tag can contain newlines. Most do not.
*
* @update gess 3/25/98
* @param aTag -- tag to test for containership
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return PR_TRUE if given tag can contain other tags
*/ //----------------------------------------------------
virtual PRBool CanDisregard(PRInt32 aParent,PRInt32 aChild)const=0;
virtual PRBool CanOmit(PRInt32 aParent,PRInt32 aChild)const=0;
/** -------------------------------------------------------
* This method does two things: 1st, help construct
@ -92,6 +93,18 @@ class nsIDTD : public nsISupports {
*/ //----------------------------------------------------
virtual PRInt32 GetDefaultParentTagFor(PRInt32 aTag) const=0;
/** -------------------------------------------------------
* This method tries to design a context map (without actually
* changing our parser state) from the parent down to the
* child.
*
* @update gess4/6/98
* @param aParent -- tag type of parent
* @param aChild -- tag type of child
* @return Non zero count of intermediate nodes;
* 0 if unable to comply
*/ //----------------------------------------------------
virtual PRInt32 CreateContextMapBetween(PRInt32 aParent,PRInt32 aChild) const=0;
};

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

@ -51,7 +51,7 @@ class nsIParser : public nsISupports {
public:
virtual void SetContentSink(nsIContentSink* aContentSink)=0;
virtual nsIContentSink* SetContentSink(nsIContentSink* aContentSink)=0;
virtual PRBool Parse(nsIURL* aURL)=0;
virtual PRBool ResumeParse()=0;
};

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

@ -39,6 +39,7 @@
#define ITOKENIZERDELEGATE
#include "prtypes.h"
#include "nsParserTypes.h"
class CScanner;
class CToken;
@ -49,8 +50,10 @@ class ITokenizerDelegate {
virtual PRBool WillTokenize()=0;
virtual PRBool DidTokenize()=0;
virtual CToken* GetToken(CScanner* aScanner,PRInt32& anErrorCode)=0;
virtual CToken* GetToken(CScanner& aScanner,PRInt32& anErrorCode)=0;
virtual PRBool WillAddToken(CToken& aToken)=0;
virtual eParseMode GetParseMode() const=0;
};
#endif

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

@ -33,7 +33,12 @@
#include "prtypes.h"
#define PRChar char
enum eParseMode {
eParseMode_unknown=0,
eParseMode_navigator,
eParseMode_other
};
const PRInt32 kNotFound = -1;
const PRInt32 kNoError = 0;

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

@ -32,11 +32,12 @@ const char* kBadHTMLText2="</BODY></HTML>";
* @param aURL -- pointer to URL to be loaded
* @return
*------------------------------------------------------*/
CScanner::CScanner(nsIURL* aURL) : mBuffer("") {
CScanner::CScanner(nsIURL* aURL,eParseMode aMode) : mBuffer("") {
NS_ASSERTION(0!=aURL,"Error: Null URL!");
mOffset=0;
mStream=0;
mTotalRead=0;
mParseMode=aMode;
if(aURL) {
PRInt32 error;
gURLRef=aURL->GetSpec();

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

@ -43,7 +43,7 @@ class ifstream;
class CScanner {
public:
CScanner(nsIURL* aURL);
CScanner(nsIURL* aURL,eParseMode aMode=eParseMode_navigator);
~CScanner();
PRInt32 GetChar(PRUnichar& ch);
@ -69,6 +69,7 @@ class CScanner {
nsString mBuffer;
PRInt32 mOffset;
PRInt32 mTotalRead;
eParseMode mParseMode;
};
#endif

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

@ -47,7 +47,7 @@ CToken::~CToken() {
* @param aScanner -- object to retrieve data from
* @return int error code
*------------------------------------------------------*/
PRInt32 CToken::Consume(PRUnichar aChar,CScanner* aScanner) {
PRInt32 CToken::Consume(PRUnichar aChar,CScanner& aScanner) {
PRInt32 result=kNoError;
return result;
}

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

@ -60,7 +60,7 @@ class CToken {
virtual void SetStringValue(const char* name);
virtual void SetOrdinal(PRInt32 value);
virtual PRInt32 GetOrdinal(void);
virtual PRInt32 Consume(PRUnichar aChar,CScanner* aScanner);
virtual PRInt32 Consume(PRUnichar aChar,CScanner& aScanner);
virtual void DebugDumpToken(ostream& out);
virtual void DebugDumpSource(ostream& out);
virtual PRInt32 GetTokenType(void);

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

@ -0,0 +1,637 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/1/98
*
*/
#include "nsTokenHandler.h"
#include "nsHTMLParser.h"
#include "nsHTMLTokens.h"
#include "nsDebug.h"
static const char* kNullParserGiven = "Error: Null parser given as argument";
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CTokenHandler::CTokenHandler(eHTMLTokenTypes aType) {
mType=aType;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CTokenHandler::~CTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
eHTMLTokenTypes CTokenHandler::GetTokenType(void){
return mType;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
PRBool result=PR_FALSE;
if(aParser){
result=PR_TRUE;
}
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CStartTokenHandler::CStartTokenHandler() : CTokenHandler(eToken_start) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CStartTokenHandler::~CStartTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CStartTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleStartToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CStartTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CEndTokenHandler::CEndTokenHandler(): CTokenHandler(eToken_end) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CEndTokenHandler::~CEndTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CEndTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleEndToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CEndTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CCommentTokenHandler::CCommentTokenHandler() : CTokenHandler(eToken_comment) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CCommentTokenHandler::~CCommentTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CCommentTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleCommentToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CCommentTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CEntityTokenHandler::CEntityTokenHandler() : CTokenHandler(eToken_entity) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CEntityTokenHandler::~CEntityTokenHandler() {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CEntityTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleEntityToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CEntityTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CWhitespaceTokenHandler::CWhitespaceTokenHandler() : CTokenHandler(eToken_whitespace) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CWhitespaceTokenHandler::~CWhitespaceTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CWhitespaceTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleWhitespaceToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CWhitespaceTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CNewlineTokenHandler::CNewlineTokenHandler() : CTokenHandler(eToken_newline) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CNewlineTokenHandler::~CNewlineTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CNewlineTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleNewlineToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CNewlineTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CTextTokenHandler::CTextTokenHandler() : CTokenHandler(eToken_text) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CTextTokenHandler::~CTextTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CTextTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleTextToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CTextTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CAttributeTokenHandler::CAttributeTokenHandler() : CTokenHandler(eToken_attribute) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CAttributeTokenHandler::~CAttributeTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CAttributeTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleAttributeToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CAttributeTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CScriptTokenHandler::CScriptTokenHandler() : CTokenHandler(eToken_script) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CScriptTokenHandler::~CScriptTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CScriptTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleScriptToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CScriptTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CStyleTokenHandler::CStyleTokenHandler() : CTokenHandler(eToken_style) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CStyleTokenHandler::~CStyleTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CStyleTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleStyleToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CStyleTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CSkippedContentTokenHandler::CSkippedContentTokenHandler() : CTokenHandler(eToken_skippedcontent) {
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
CSkippedContentTokenHandler::~CSkippedContentTokenHandler(){
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CSkippedContentTokenHandler::operator()(CToken* aToken,nsHTMLParser* aParser){
NS_ASSERTION(0!=aParser,kNullParserGiven);
if(aParser){
return aParser->HandleSkippedContentToken(aToken);
}
return PR_FALSE;
}
/**-------------------------------------------------------
*
*
* @update gess 4/2/98
* @param
* @return
*------------------------------------------------------*/
PRBool CSkippedContentTokenHandler::CanHandle(eHTMLTokenTypes aType){
PRBool result=PR_FALSE;
return result;
}

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

@ -0,0 +1,161 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/*
* The contents of this file are subject to the Netscape Public License
* Version 1.0 (the "NPL"); you may not use this file except in
* compliance with the NPL. You may obtain a copy of the NPL at
* http://www.mozilla.org/NPL/
*
* Software distributed under the NPL is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
* for the specific language governing rights and limitations under the
* NPL.
*
* The Initial Developer of this code under the NPL is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
* Reserved.
*/
/**
* MODULE NOTES:
* @update gess 4/1/98
*
*/
#ifndef CTokenHandler__
#define CTokenHandler__
#include "prtypes.h"
#include "nsString.h"
#include "nsHTMLTokens.h"
#include "nsITokenHandler.h"
class CToken;
class nsHTMLParser;
class CTokenHandler : public CITokenHandler {
public:
CTokenHandler(eHTMLTokenTypes aType=eToken_unknown);
virtual ~CTokenHandler();
virtual eHTMLTokenTypes GetTokenType(void);
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
protected:
eHTMLTokenTypes mType;
};
class CStartTokenHandler : public CTokenHandler {
public:
CStartTokenHandler();
virtual ~CStartTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CEndTokenHandler : public CTokenHandler {
public:
CEndTokenHandler();
virtual ~CEndTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CCommentTokenHandler : public CTokenHandler {
public:
CCommentTokenHandler();
virtual ~CCommentTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CEntityTokenHandler : public CTokenHandler {
public:
CEntityTokenHandler();
virtual ~CEntityTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CWhitespaceTokenHandler : public CTokenHandler {
public:
CWhitespaceTokenHandler();
virtual ~CWhitespaceTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CNewlineTokenHandler : public CTokenHandler {
public:
CNewlineTokenHandler();
virtual ~CNewlineTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CTextTokenHandler : public CTokenHandler {
public:
CTextTokenHandler();
virtual ~CTextTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CAttributeTokenHandler : public CTokenHandler {
public:
CAttributeTokenHandler();
virtual ~CAttributeTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CScriptTokenHandler : public CTokenHandler {
public:
CScriptTokenHandler();
virtual ~CScriptTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CStyleTokenHandler : public CTokenHandler {
public:
CStyleTokenHandler();
virtual ~CStyleTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
class CSkippedContentTokenHandler : public CTokenHandler {
public:
CSkippedContentTokenHandler();
virtual ~CSkippedContentTokenHandler();
virtual PRBool operator()(CToken* aToken,nsHTMLParser* aParser);
virtual PRBool CanHandle(eHTMLTokenTypes aType);
};
#endif

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

@ -19,7 +19,6 @@
#include <fstream.h>
#include "nsTokenizer.h"
#include "nsITokenizerDelegate.h"
#include "nsToken.h"
#include "nsScanner.h"
#include "nsIURL.h"
@ -33,10 +32,11 @@
* @param aDelegate -- ref to delegate to be used to tokenize
* @return
*------------------------------------------------------*/
CTokenizer::CTokenizer(nsIURL* aURL,ITokenizerDelegate& aDelegate) :
mDelegate(aDelegate),
CTokenizer::CTokenizer(nsIURL* aURL,ITokenizerDelegate* aDelegate,eParseMode aMode) :
mTokenDeque() {
mScanner= new CScanner(aURL);
mDelegate=aDelegate;
mScanner=new CScanner(aURL,aMode);
mParseMode=aMode;
}
@ -48,6 +48,20 @@ CTokenizer::CTokenizer(nsIURL* aURL,ITokenizerDelegate& aDelegate) :
* @return
*------------------------------------------------------*/
CTokenizer::~CTokenizer() {
delete mScanner;
delete mDelegate;
mScanner=0;
}
/**
* Retrieve a reference to the internal token deque.
*
* @update gess 4/20/98
* @return deque reference
*/
nsDeque& CTokenizer::GetDeque(void) {
return mTokenDeque;
}
/**-------------------------------------------------------
@ -59,7 +73,7 @@ CTokenizer::~CTokenizer() {
* @return new token or null
*------------------------------------------------------*/
CToken* CTokenizer::GetToken(PRInt32& anError) {
CToken* nextToken=mDelegate.GetToken(mScanner,anError);
CToken* nextToken=mDelegate->GetToken(*mScanner,anError);
return nextToken;
}
@ -86,7 +100,7 @@ PRInt32 CTokenizer::GetSize(void) {
*------------------------------------------------------*/
PRBool CTokenizer::WillTokenize(){
PRBool result=PR_TRUE;
result=mDelegate.WillTokenize();
result=mDelegate->WillTokenize();
return result;
}
@ -110,7 +124,7 @@ PRInt32 CTokenizer::Tokenize(void) {
#ifdef VERBOSE_DEBUG
nextToken->DebugDumpToken(cout);
#endif
if(mDelegate.WillAddToken(*nextToken)) {
if(mDelegate->WillAddToken(*nextToken)) {
mTokenDeque.Push(nextToken);
}
}
@ -131,7 +145,12 @@ PRInt32 CTokenizer::Tokenize(void) {
* @return TRUE if all went well
*------------------------------------------------------*/
PRBool CTokenizer::DidTokenize() {
PRBool result=mDelegate.DidTokenize();
PRBool result=mDelegate->DidTokenize();
#ifdef VERBOSE_DEBUG
DebugDumpTokens(cout);
#endif
return result;
}
@ -145,12 +164,12 @@ PRBool CTokenizer::DidTokenize() {
* @return
*------------------------------------------------------*/
void CTokenizer::DebugDumpTokens(ostream& out) {
CDequeIterator b=mTokenDeque.Begin();
CDequeIterator e=mTokenDeque.End();
nsDequeIterator b=mTokenDeque.Begin();
nsDequeIterator e=mTokenDeque.End();
CToken* theToken;
while(b!=e) {
theToken=(b++);
theToken=(CToken*)(b++);
theToken->DebugDumpToken(out);
}
}
@ -166,12 +185,12 @@ void CTokenizer::DebugDumpTokens(ostream& out) {
* @return
*------------------------------------------------------*/
void CTokenizer::DebugDumpSource(ostream& out) {
CDequeIterator b=mTokenDeque.Begin();
CDequeIterator e=mTokenDeque.End();
nsDequeIterator b=mTokenDeque.Begin();
nsDequeIterator e=mTokenDeque.End();
CToken* theToken;
while(b!=e) {
theToken=(b++);
theToken=(CToken*)(b++);
theToken->DebugDumpSource(out);
}

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

@ -50,13 +50,13 @@ class nsIURL;
class CTokenizer {
public:
CTokenizer(nsIURL* aURL,ITokenizerDelegate& aDelegate);
CTokenizer(nsIURL* aURL,ITokenizerDelegate* aDelegate,eParseMode aMode);
~CTokenizer();
PRInt32 Tokenize(void);
CToken* GetToken(PRInt32& anErrorCode);
PRInt32 GetSize(void);
CDeque& GetDeque(void) {return mTokenDeque;}
nsDeque& GetDeque(void);
void DebugDumpSource(ostream& out);
void DebugDumpTokens(ostream& out);
@ -67,9 +67,10 @@ class CTokenizer {
PRBool WillTokenize();
PRBool DidTokenize();
ITokenizerDelegate& mDelegate;
ITokenizerDelegate* mDelegate;
CScanner* mScanner;
CDeque mTokenDeque;
nsDeque mTokenDeque;
eParseMode mParseMode;
};
#endif