mCurrentPos->GetCurrent();
-
+
/**************************************************************************
The point of this code to serve as a testbed for parser reentrancy.
If you set recurse=1, we go reentrant, passing a text string of HTML onto
the parser for inline processing, just like javascript/DOM would do it.
And guess what? It worked the first time!
- Uncomment the following code to enable the test:
+ Uncomment the following code to enable the test:
int recurse=0;
if(recurse){
- nsString theString("");
+ nsString theString(" this is just a great big empty string ");
+// nsString theString("doc.write");
+// nsString theString("
");
Parse(theString,PR_TRUE);
}
- **************************************************************************/
+ */
theMarkPos=*mParserContext->mCurrentPos;
- result=mParserContext->mDTD->HandleToken(theToken);
+
+ result=theRootDTD->HandleToken(theToken);
+// result=mParserContext->mDTD->HandleToken(theToken);
++(*mParserContext->mCurrentPos);
}
@@ -813,10 +828,11 @@ PRBool nsParser::WillTokenize(){
PRInt32 nsParser::Tokenize(){
CToken* theToken=0;
PRInt32 result=kNoError;
- PRBool done=(0==++mMajorIteration) ? (!WillTokenize()) : PR_FALSE;
-
- while((PR_FALSE==done) && (kNoError==result)) {
+ ++mMajorIteration;
+
+ WillTokenize();
+ while(kNoError==result) {
mParserContext->mScanner->Mark();
result=mParserContext->mDTD->ConsumeToken(theToken);
if(kNoError==result) {
@@ -835,8 +851,7 @@ PRInt32 nsParser::Tokenize(){
mParserContext->mScanner->RewindToMark();
}
}
- if((PR_TRUE==done) && (kInterrupted!=result))
- DidTokenize();
+ DidTokenize();
return result;
}
@@ -851,11 +866,6 @@ PRInt32 nsParser::Tokenize(){
*/
PRBool nsParser::DidTokenize(){
PRBool result=PR_TRUE;
-
-#ifdef VERBOSE_DEBUG
- DebugDumpTokens(cout);
-#endif
-
return result;
}
diff --git a/mozilla/htmlparser/src/nsParser.h b/mozilla/htmlparser/src/nsParser.h
index 4c2056a6d3a..ce06eb452ff 100644
--- a/mozilla/htmlparser/src/nsParser.h
+++ b/mozilla/htmlparser/src/nsParser.h
@@ -294,14 +294,13 @@ protected:
CParserContext* mParserContext;
PRInt32 mMajorIteration;
PRInt32 mMinorIteration;
+ PRInt32 mParseLevel;
nsIStreamObserver* mObserver;
nsIContentSink* mSink;
nsIParserFilter* mParserFilter;
nsIDTDDebug* mDTDDebug;
-
-
};
diff --git a/mozilla/htmlparser/src/nsParserTypes.h b/mozilla/htmlparser/src/nsParserTypes.h
index 83a1e91b308..9bad92f2a14 100644
--- a/mozilla/htmlparser/src/nsParserTypes.h
+++ b/mozilla/htmlparser/src/nsParserTypes.h
@@ -43,13 +43,13 @@ enum eParseMode {
};
-const PRInt32 kEOF = 1000000L;
-const PRInt32 kUnknownError = -1000;
-const PRInt32 kCantPropagate = -6;
-const PRInt32 kContextMismatch = -5;
-const PRInt32 kBadFilename = -4;
-const PRInt32 kBadURL = -3;
-const PRInt32 kInterrupted = -2;
+const PRInt32 kEOF = 10000;
+const PRInt32 kUnknownError = 10001;
+const PRInt32 kCantPropagate = 10002;
+const PRInt32 kContextMismatch = 10003;
+const PRInt32 kBadFilename = 10004;
+const PRInt32 kBadURL = 10005;
+const PRInt32 kInterrupted = 10006;
const PRInt32 kNotFound = -1;
const PRInt32 kNoError = NS_OK;
diff --git a/mozilla/htmlparser/src/nsScanner.cpp b/mozilla/htmlparser/src/nsScanner.cpp
index 93ce54eea57..938202153a5 100644
--- a/mozilla/htmlparser/src/nsScanner.cpp
+++ b/mozilla/htmlparser/src/nsScanner.cpp
@@ -31,8 +31,27 @@ const int kBufsize=64;
/**
- * Use this constructor if you want i/o to be based on an
- * incremental netstream. If you pass a null filename, you
+ * Use this constructor if you want i/o to be based on
+ * a single string you hand in during construction.
+ * This short cut was added for Javascript.
+ *
+ * @update gess 5/12/98
+ * @param aMode represents the parser mode (nav, other)
+ * @return
+ */
+CScanner::CScanner(nsString& anHTMLString) :
+ mBuffer(anHTMLString), mFilename("")
+{
+ mTotalRead=mBuffer.Length();
+ mIncremental=PR_FALSE;
+ mOwnsStream=PR_FALSE;
+ mOffset=0;
+ mFileStream=0;
+}
+
+/**
+ * Use this constructor if you want i/o to be based on strings
+ * the scanner receives. If you pass a null filename, you
* can still provide data to the scanner via append.
*
* @update gess 5/12/98
@@ -42,6 +61,7 @@ const int kBufsize=64;
CScanner::CScanner(nsString& aFilename,PRBool aCreateStream) :
mBuffer(""), mFilename(aFilename)
{
+ mIncremental=PR_TRUE;
mOffset=0;
mMarkPos=-1;
mTotalRead=0;
@@ -71,6 +91,7 @@ CScanner::CScanner(nsString& aFilename,PRBool aCreateStream) :
CScanner::CScanner(nsString& aFilename,fstream& aStream,PRBool assumeOwnership) :
mBuffer(""), mFilename(aFilename)
{
+ mIncremental=PR_TRUE;
mOffset=0;
mMarkPos=-1;
mTotalRead=0;
@@ -135,26 +156,17 @@ void _PreCompressBuffer(nsString& aBuffer,PRInt32& anOffset,PRInt32& aMarkPos){
//we've guaranteed the client we can back up to, so make sure
//you don't lose any of the data beyond that point.
-/*
- if((anOffset!=aMarkPos) && (0<=aMarkPos)) {
- if(aMarkPos>0) {
- aBuffer.Cut(0,aMarkPos);
- if(anOffset>aMarkPos)
- anOffset-=aMarkPos;
- }
- }
- else aBuffer.Truncate();
-*/
PRInt32 len=aBuffer.Length();
- if((aMarkPos=0)) {
+ if((aMarkPos0)) {
aBuffer.Cut(0,aMarkPos);
anOffset-=aMarkPos;
+ aMarkPos=0;
}
- else {
+ else if((anOffset==aMarkPos) && (0WillBuildModel();
}
@@ -430,13 +440,14 @@ nsresult CNavDTD::WillBuildModel(nsString& aFilename){
* @param
* @return
*/
-nsresult CNavDTD::DidBuildModel(PRInt32 anErrorCode){
+nsresult CNavDTD::DidBuildModel(PRInt32 anErrorCode,PRInt32 aLevel){
nsresult result= NS_OK;
if((kNoError==anErrorCode) && (mContextStack.mCount>0)) {
result = CloseContainersTo(0,eHTMLTag_unknown,PR_FALSE);
}
- if(mSink) {
+
+ if((1==aLevel) && (mSink)) {
result = mSink->DidBuildModel(1);
}
@@ -2843,8 +2854,7 @@ CNavDTD::ConsumeWhitespace(PRUnichar aChar,
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*/
-nsresult
-CNavDTD::ConsumeComment(PRUnichar aChar,CScanner& aScanner,CToken*& aToken){
+nsresult CNavDTD::ConsumeComment(PRUnichar aChar,CScanner& aScanner,CToken*& aToken){
aToken = new CCommentToken();
nsresult result=NS_OK;
if(aToken) {
@@ -2863,14 +2873,18 @@ CNavDTD::ConsumeComment(PRUnichar aChar,CScanner& aScanner,CToken*& aToken){
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*/
-nsresult
-CNavDTD::ConsumeText(const nsString& aString,
- CScanner& aScanner,
- CToken*& aToken){
+nsresult CNavDTD::ConsumeText(const nsString& aString,CScanner& aScanner,CToken*& aToken){
nsresult result=NS_OK;
if(aToken=new CTextToken(aString)) {
PRUnichar ch=0;
result=aToken->Consume(ch,aScanner);
+ if(result) {
+ nsString& temp=aToken->GetStringValueXXX();
+ if(0==temp.Length()){
+ delete aToken;
+ }
+ else result=kNoError;
+ }
}
return result;
}
@@ -2884,10 +2898,7 @@ CNavDTD::ConsumeText(const nsString& aString,
* @param anErrorCode: arg that will hold error condition
* @return new token or null
*/
-nsresult
-CNavDTD::ConsumeNewline(PRUnichar aChar,
- CScanner& aScanner,
- CToken*& aToken){
+nsresult CNavDTD::ConsumeNewline(PRUnichar aChar,CScanner& aScanner,CToken*& aToken){
aToken=new CNewlineToken();
nsresult result=NS_OK;
if(aToken) {
@@ -2918,7 +2929,6 @@ nsresult CNavDTD::ConsumeToken(CToken*& aToken){
nsresult result=NS_OK;
CScanner* theScanner=mParser->GetScanner();
if(NS_OK==result){
-
PRUnichar theChar;
result=theScanner->GetChar(theChar);
switch(result) {
@@ -2933,13 +2943,16 @@ nsresult CNavDTD::ConsumeToken(CToken*& aToken){
default:
switch(theChar) {
case kLessThan:
- return ConsumeTag(theChar,*theScanner,aToken);
+ result=ConsumeTag(theChar,*theScanner,aToken);
+ break;
case kAmpersand:
- return ConsumeEntity(theChar,*theScanner,aToken);
+ result=ConsumeEntity(theChar,*theScanner,aToken);
+ break;
case kCR: case kLF:
- return ConsumeNewline(theChar,*theScanner,aToken);
+ result=ConsumeNewline(theChar,*theScanner,aToken);
+ break;
case kNotFound:
break;
@@ -2947,15 +2960,17 @@ nsresult CNavDTD::ConsumeToken(CToken*& aToken){
default:
if(!nsString::IsSpace(theChar)) {
nsAutoString temp(theChar);
- return ConsumeText(temp,*theScanner,aToken);
+ result=ConsumeText(temp,*theScanner,aToken);
+ break;
}
- return ConsumeWhitespace(theChar,*theScanner,aToken);
+ result=ConsumeWhitespace(theChar,*theScanner,aToken);
+ break;
} //switch
break;
} //switch
- if(NS_OK==result)
- result=theScanner->Eof();
- } //while
+// if(NS_OK==result)
+// result=theScanner->Eof();
+ } //if
return result;
}
diff --git a/mozilla/parser/htmlparser/src/CNavDTD.h b/mozilla/parser/htmlparser/src/CNavDTD.h
index 5bb10e4713c..93a8635942a 100644
--- a/mozilla/parser/htmlparser/src/CNavDTD.h
+++ b/mozilla/parser/htmlparser/src/CNavDTD.h
@@ -170,6 +170,15 @@ CLASS_EXPORT_HTMLPARS CNavDTD : public nsIDTD {
*/
virtual ~CNavDTD();
+ /**
+ * Call this method if you want the DTD to construct a clone of itself.
+ * @update gess7/23/98
+ * @param
+ * @return
+ */
+ virtual nsresult CreateNewInstance(nsIDTD** aInstancePtrResult);
+
+
NS_DECL_ISUPPORTS
/**
@@ -212,7 +221,7 @@ CLASS_EXPORT_HTMLPARS CNavDTD : public nsIDTD {
* @param aFilename is the name of the file being parsed.
* @return error code (almost always 0)
*/
- NS_IMETHOD WillBuildModel(nsString& aFilename);
+ NS_IMETHOD WillBuildModel(nsString& aFilename,PRInt32 aLevel);
/**
* The parser uses a code sandwich to wrap the parsing process. Before
@@ -222,7 +231,7 @@ CLASS_EXPORT_HTMLPARS CNavDTD : public nsIDTD {
* @param anErrorCode contans the last error that occured
* @return error code
*/
- NS_IMETHOD DidBuildModel(PRInt32 anErrorCode);
+ NS_IMETHOD DidBuildModel(PRInt32 anErrorCode,PRInt32 aLevel);
/**
* This method is called by the parser, once for each token
diff --git a/mozilla/parser/htmlparser/src/COtherDTD.cpp b/mozilla/parser/htmlparser/src/COtherDTD.cpp
index 862933dd973..7389cb3d5b2 100644
--- a/mozilla/parser/htmlparser/src/COtherDTD.cpp
+++ b/mozilla/parser/htmlparser/src/COtherDTD.cpp
@@ -148,6 +148,17 @@ COtherDTD::~COtherDTD(){
//parent does all the real work of destruction.
}
+/**
+ * Call this method if you want the DTD to construct a fresh instance
+ * of itself
+ * @update gess7/23/98
+ * @param
+ * @return
+ */
+nsresult COtherDTD::CreateNewInstance(nsIDTD** aInstancePtrResult){
+ return NS_NewOtherHTMLDTD(aInstancePtrResult);
+}
+
/**
* This method is called to determine if the given DTD can parse
* a document in a given source-type.
@@ -178,8 +189,8 @@ eAutoDetectResult COtherDTD::AutoDetectContentType(nsString& aBuffer,nsString& a
* @param
* @return
*/
-NS_IMETHODIMP COtherDTD::WillBuildModel(nsString& aFilename) {
- return CNavDTD::WillBuildModel(aFilename);
+NS_IMETHODIMP COtherDTD::WillBuildModel(nsString& aFilename,PRInt32 aLevel) {
+ return CNavDTD::WillBuildModel(aFilename, aLevel);
}
/**
@@ -188,8 +199,8 @@ NS_IMETHODIMP COtherDTD::WillBuildModel(nsString& aFilename) {
* @param
* @return
*/
-NS_IMETHODIMP COtherDTD::DidBuildModel(PRInt32 anErrorCode){
- return CNavDTD::DidBuildModel(anErrorCode);
+NS_IMETHODIMP COtherDTD::DidBuildModel(PRInt32 anErrorCode,PRInt32 aLevel){
+ return CNavDTD::DidBuildModel(anErrorCode, aLevel);
}
/**
diff --git a/mozilla/parser/htmlparser/src/COtherDTD.h b/mozilla/parser/htmlparser/src/COtherDTD.h
index 10be7a27ab1..77c88a8f8c5 100644
--- a/mozilla/parser/htmlparser/src/COtherDTD.h
+++ b/mozilla/parser/htmlparser/src/COtherDTD.h
@@ -62,6 +62,14 @@ class COtherDTD : public CNavDTD {
*/
virtual ~COtherDTD();
+ /**
+ * Call this method if you want the DTD to construct a clone of itself.
+ * @update gess7/23/98
+ * @param
+ * @return
+ */
+ virtual nsresult CreateNewInstance(nsIDTD** aInstancePtrResult);
+
/**
* This method is called to determine if the given DTD can parse
* a document in a given source-type.
@@ -82,20 +90,24 @@ class COtherDTD : public CNavDTD {
virtual eAutoDetectResult AutoDetectContentType(nsString& aBuffer,nsString& aType);
/**
- *
- * @update gess5/18/98
- * @param
- * @return
- */
- NS_IMETHOD WillBuildModel(nsString& aString);
+ * The parser uses a code sandwich to wrap the parsing process. Before
+ * the process begins, WillBuildModel() is called. Afterwards the parser
+ * calls DidBuildModel().
+ * @update gess5/18/98
+ * @param aFilename is the name of the file being parsed.
+ * @return error code (almost always 0)
+ */
+ NS_IMETHOD WillBuildModel(nsString& aFilename,PRInt32 aLevel);
- /**
- *
+ /**
+ * The parser uses a code sandwich to wrap the parsing process. Before
+ * the process begins, WillBuildModel() is called. Afterwards the parser
+ * calls DidBuildModel().
* @update gess5/18/98
- * @param
- * @return
+ * @param anErrorCode contans the last error that occured
+ * @return error code
*/
- NS_IMETHOD DidBuildModel(PRInt32 anErrorCode);
+ NS_IMETHOD DidBuildModel(PRInt32 anErrorCode,PRInt32 aLevel);
/**
*
diff --git a/mozilla/parser/htmlparser/src/CParserContext.cpp b/mozilla/parser/htmlparser/src/CParserContext.cpp
index e089510777d..35eeff728d0 100644
--- a/mozilla/parser/htmlparser/src/CParserContext.cpp
+++ b/mozilla/parser/htmlparser/src/CParserContext.cpp
@@ -33,6 +33,15 @@ public:
CTokenDeallocator gTokenDeallocator;
+
+/**
+ * Your friendly little constructor. Ok, it's not the friendly, but the only guy
+ * using it is the parser.
+ * @update gess7/23/98
+ * @param aScanner
+ * @param aKey
+ * @param aListener
+ */
CParserContext::CParserContext(CScanner* aScanner,void* aKey,nsIStreamObserver* aListener) :
mSourceType(),
mTokenDeque(gTokenDeallocator)
@@ -69,8 +78,9 @@ CParserContext::~CParserContext(){
if(mTransferBuffer)
delete [] mTransferBuffer;
- //Remember that it's ok to simply
- //ignore the DTD and the prevcontext.
+ NS_RELEASE(mDTD);
+
+ //Remember that it's ok to simply ingore the PrevContext.
}
diff --git a/mozilla/parser/htmlparser/src/CRtfDTD.cpp b/mozilla/parser/htmlparser/src/CRtfDTD.cpp
index 5c06e0ae06d..94a5784c9ad 100644
--- a/mozilla/parser/htmlparser/src/CRtfDTD.cpp
+++ b/mozilla/parser/htmlparser/src/CRtfDTD.cpp
@@ -216,6 +216,17 @@ CRtfDTD::CRtfDTD() : nsIDTD() {
CRtfDTD::~CRtfDTD(){
}
+/**
+ * Call this method if you want the DTD to construct fresh instance
+ * of itself.
+ * @update gess7/23/98
+ * @param
+ * @return
+ */
+nsresult CRtfDTD::CreateNewInstance(nsIDTD** aInstancePtrResult){
+ return NS_NewRTF_DTD(aInstancePtrResult);
+}
+
/**
* This method is called to determine if the given DTD can parse
* a document in a given source-type.
@@ -251,7 +262,7 @@ eAutoDetectResult CRtfDTD::AutoDetectContentType(nsString& aBuffer,nsString& aTy
* @param
* @return
*/
-NS_IMETHODIMP CRtfDTD::WillBuildModel(nsString& aFilename){
+NS_IMETHODIMP CRtfDTD::WillBuildModel(nsString& aFilename,PRInt32 aLevel){
nsresult result=NS_OK;
return result;
}
@@ -262,7 +273,7 @@ NS_IMETHODIMP CRtfDTD::WillBuildModel(nsString& aFilename){
* @param
* @return
*/
-NS_IMETHODIMP CRtfDTD::DidBuildModel(PRInt32 anErrorCode){
+NS_IMETHODIMP CRtfDTD::DidBuildModel(PRInt32 anErrorCode,PRInt32 aLevel){
nsresult result=NS_OK;
return result;
diff --git a/mozilla/parser/htmlparser/src/CRtfDTD.h b/mozilla/parser/htmlparser/src/CRtfDTD.h
index d2a0df8d694..020b9a7c60c 100644
--- a/mozilla/parser/htmlparser/src/CRtfDTD.h
+++ b/mozilla/parser/htmlparser/src/CRtfDTD.h
@@ -165,6 +165,14 @@ class CRtfDTD : public nsIDTD {
*/
virtual ~CRtfDTD();
+ /**
+ * Call this method if you want the DTD to construct a clone of itself.
+ * @update gess7/23/98
+ * @param
+ * @return
+ */
+ virtual nsresult CreateNewInstance(nsIDTD** aInstancePtrResult);
+
/**
* This method is called to determine if the given DTD can parse
* a document in a given source-type.
@@ -185,20 +193,24 @@ class CRtfDTD : public nsIDTD {
virtual eAutoDetectResult AutoDetectContentType(nsString& aBuffer,nsString& aType);
/**
- *
- * @update gess5/18/98
- * @param
- * @return
- */
- NS_IMETHOD WillBuildModel(nsString& aFilename);
+ * The parser uses a code sandwich to wrap the parsing process. Before
+ * the process begins, WillBuildModel() is called. Afterwards the parser
+ * calls DidBuildModel().
+ * @update gess5/18/98
+ * @param aFilename is the name of the file being parsed.
+ * @return error code (almost always 0)
+ */
+ NS_IMETHOD WillBuildModel(nsString& aFilename,PRInt32 aLevel);
- /**
- *
+ /**
+ * The parser uses a code sandwich to wrap the parsing process. Before
+ * the process begins, WillBuildModel() is called. Afterwards the parser
+ * calls DidBuildModel().
* @update gess5/18/98
- * @param
- * @return
+ * @param anErrorCode contans the last error that occured
+ * @return error code
*/
- NS_IMETHOD DidBuildModel(PRInt32 anErrorCode);
+ NS_IMETHOD DidBuildModel(PRInt32 anErrorCode,PRInt32 aLevel);
/**
*
diff --git a/mozilla/parser/htmlparser/src/nsIDTD.h b/mozilla/parser/htmlparser/src/nsIDTD.h
index 4d48349be3c..833432bea6f 100644
--- a/mozilla/parser/htmlparser/src/nsIDTD.h
+++ b/mozilla/parser/htmlparser/src/nsIDTD.h
@@ -49,12 +49,22 @@ enum eAutoDetectResult {eUnknownDetect, eValidDetect, eInvalidDetect};
class nsIDTD : public nsISupports {
public:
+
/**
* Default constructor
* @update gess6/24/98
*/
virtual ~nsIDTD() {};
+
+ /**
+ * Call this method if you want the DTD to construct a clone of itself.
+ * @update gess7/23/98
+ * @param
+ * @return
+ */
+ virtual nsresult CreateNewInstance(nsIDTD** aInstancePtrResult)=0;
+
/**
* This method informs the DTD about the parser being used to drive the parse process
*
@@ -100,7 +110,7 @@ class nsIDTD : public nsISupports {
* @param aFilename--string that contains name of file being parsed (if applicable)
* @return
*/
- NS_IMETHOD WillBuildModel(nsString& aFilename)=0;
+ NS_IMETHOD WillBuildModel(nsString& aFilename,PRInt32 aLevel)=0;
/**
* Called by the parser after the parsing process has concluded
@@ -108,7 +118,7 @@ class nsIDTD : public nsISupports {
* @param anErrorCode - contains error code resulting from parse process
* @return
*/
- NS_IMETHOD DidBuildModel(PRInt32 anErrorCode)=0;
+ NS_IMETHOD DidBuildModel(PRInt32 anErrorCode,PRInt32 aLevel)=0;
/**
* Called during model building phase of parse process. Each token created during
diff --git a/mozilla/parser/htmlparser/src/nsParser.cpp b/mozilla/parser/htmlparser/src/nsParser.cpp
index 9e4b34516b5..b86b40e1c89 100644
--- a/mozilla/parser/htmlparser/src/nsParser.cpp
+++ b/mozilla/parser/htmlparser/src/nsParser.cpp
@@ -142,6 +142,7 @@ nsParser::nsParser() {
mObserver = 0;
mSink=0;
mParserContext=0;
+ mParseLevel=0;
}
@@ -319,7 +320,7 @@ PRBool FindSuitableDTD( CParserContext& aParserContext) {
if(theDTD) {
result=theDTD->CanParse(aParserContext.mSourceType,0);
if(result){
- aParserContext.mDTD=theDTD;
+ nsresult status=theDTD->CreateNewInstance(&aParserContext.mDTD);
break;
}
}
@@ -385,7 +386,7 @@ PRInt32 nsParser::WillBuildModel(nsString& aFilename){
if(PR_TRUE==FindSuitableDTD(*mParserContext)) {
mParserContext->mDTD->SetParser(this);
mParserContext->mDTD->SetContentSink(mSink);
- mParserContext->mDTD->WillBuildModel(aFilename);
+ mParserContext->mDTD->WillBuildModel(aFilename,mParseLevel);
}
return kNoError;
@@ -401,7 +402,7 @@ PRInt32 nsParser::DidBuildModel(PRInt32 anErrorCode) {
//One last thing...close any open containers.
PRInt32 result=anErrorCode;
if(mParserContext->mDTD) {
- result=mParserContext->mDTD->DidBuildModel(anErrorCode);
+ result=mParserContext->mDTD->DidBuildModel(anErrorCode,mParseLevel);
}
return result;
@@ -454,6 +455,7 @@ PRInt32 nsParser::Parse(nsIURL* aURL,nsIStreamObserver* aListener, nsIDTDDebug *
NS_PRECONDITION(0!=aURL,kNullURL);
PRInt32 status=kBadURL;
+ mParseLevel++;
/* Disable DTD Debug for now...
mDTDDebug = aDTDDebug;
@@ -479,6 +481,7 @@ PRInt32 nsParser::Parse(nsIURL* aURL,nsIStreamObserver* aListener, nsIDTDDebug *
PRInt32 nsParser::Parse(fstream& aStream){
PRInt32 status=kNoError;
+ mParseLevel++;
//ok, time to create our tokenizer and begin the process
CParserContext* pc=new CParserContext(new CScanner(kUnknownFilename,aStream,PR_FALSE),&aStream,0);
@@ -511,12 +514,13 @@ PRInt32 nsParser::Parse(fstream& aStream){
*/
PRInt32 nsParser::Parse(nsString& aSourceBuffer,PRBool anHTMLString){
PRInt32 result=kNoError;
+ mParseLevel++;
CParserContext* pc=new CParserContext(new CScanner(kUnknownFilename,PR_FALSE),&aSourceBuffer,0);
+
PushContext(*pc);
if(PR_TRUE==anHTMLString)
pc->mSourceType="text/html";
- mParserContext->mScanner->Append(aSourceBuffer);
if(eValidDetect==AutoDetectContentType(aSourceBuffer,mParserContext->mSourceType)) {
WillBuildModel(mParserContext->mScanner->GetFilename());
result=ResumeParse();
@@ -543,9 +547,9 @@ PRInt32 nsParser::ResumeParse() {
mParserContext->mDTD->WillResumeParse();
if(kNoError==result) {
result=Tokenize();
+ BuildModel();
if(kInterrupted==result)
mParserContext->mDTD->WillInterruptParse();
- BuildModel();
}
return result;
}
@@ -566,27 +570,38 @@ PRInt32 nsParser::BuildModel() {
if(!mParserContext->mCurrentPos)
mParserContext->mCurrentPos=new nsDequeIterator(mParserContext->mTokenDeque.Begin());
+ //Get the root DTD for use in model building...
+ CParserContext* theRootContext=mParserContext;
+ while(theRootContext->mPrevContext)
+ theRootContext=theRootContext->mPrevContext;
+
+ nsIDTD* theRootDTD=theRootContext->mDTD;
+
PRInt32 result=kNoError;
while((kNoError==result) && ((*mParserContext->mCurrentPosmCurrentPos->GetCurrent();
-
+
/**************************************************************************
The point of this code to serve as a testbed for parser reentrancy.
If you set recurse=1, we go reentrant, passing a text string of HTML onto
the parser for inline processing, just like javascript/DOM would do it.
And guess what? It worked the first time!
- Uncomment the following code to enable the test:
+ Uncomment the following code to enable the test:
int recurse=0;
if(recurse){
- nsString theString("");
+ nsString theString(" this is just a great big empty string ");
+// nsString theString("doc.write");
+// nsString theString("
");
Parse(theString,PR_TRUE);
}
- **************************************************************************/
+ */
theMarkPos=*mParserContext->mCurrentPos;
- result=mParserContext->mDTD->HandleToken(theToken);
+
+ result=theRootDTD->HandleToken(theToken);
+// result=mParserContext->mDTD->HandleToken(theToken);
++(*mParserContext->mCurrentPos);
}
@@ -813,10 +828,11 @@ PRBool nsParser::WillTokenize(){
PRInt32 nsParser::Tokenize(){
CToken* theToken=0;
PRInt32 result=kNoError;
- PRBool done=(0==++mMajorIteration) ? (!WillTokenize()) : PR_FALSE;
-
- while((PR_FALSE==done) && (kNoError==result)) {
+ ++mMajorIteration;
+
+ WillTokenize();
+ while(kNoError==result) {
mParserContext->mScanner->Mark();
result=mParserContext->mDTD->ConsumeToken(theToken);
if(kNoError==result) {
@@ -835,8 +851,7 @@ PRInt32 nsParser::Tokenize(){
mParserContext->mScanner->RewindToMark();
}
}
- if((PR_TRUE==done) && (kInterrupted!=result))
- DidTokenize();
+ DidTokenize();
return result;
}
@@ -851,11 +866,6 @@ PRInt32 nsParser::Tokenize(){
*/
PRBool nsParser::DidTokenize(){
PRBool result=PR_TRUE;
-
-#ifdef VERBOSE_DEBUG
- DebugDumpTokens(cout);
-#endif
-
return result;
}
diff --git a/mozilla/parser/htmlparser/src/nsParser.h b/mozilla/parser/htmlparser/src/nsParser.h
index 4c2056a6d3a..ce06eb452ff 100644
--- a/mozilla/parser/htmlparser/src/nsParser.h
+++ b/mozilla/parser/htmlparser/src/nsParser.h
@@ -294,14 +294,13 @@ protected:
CParserContext* mParserContext;
PRInt32 mMajorIteration;
PRInt32 mMinorIteration;
+ PRInt32 mParseLevel;
nsIStreamObserver* mObserver;
nsIContentSink* mSink;
nsIParserFilter* mParserFilter;
nsIDTDDebug* mDTDDebug;
-
-
};
diff --git a/mozilla/parser/htmlparser/src/nsParserTypes.h b/mozilla/parser/htmlparser/src/nsParserTypes.h
index 83a1e91b308..9bad92f2a14 100644
--- a/mozilla/parser/htmlparser/src/nsParserTypes.h
+++ b/mozilla/parser/htmlparser/src/nsParserTypes.h
@@ -43,13 +43,13 @@ enum eParseMode {
};
-const PRInt32 kEOF = 1000000L;
-const PRInt32 kUnknownError = -1000;
-const PRInt32 kCantPropagate = -6;
-const PRInt32 kContextMismatch = -5;
-const PRInt32 kBadFilename = -4;
-const PRInt32 kBadURL = -3;
-const PRInt32 kInterrupted = -2;
+const PRInt32 kEOF = 10000;
+const PRInt32 kUnknownError = 10001;
+const PRInt32 kCantPropagate = 10002;
+const PRInt32 kContextMismatch = 10003;
+const PRInt32 kBadFilename = 10004;
+const PRInt32 kBadURL = 10005;
+const PRInt32 kInterrupted = 10006;
const PRInt32 kNotFound = -1;
const PRInt32 kNoError = NS_OK;
diff --git a/mozilla/parser/htmlparser/src/nsScanner.cpp b/mozilla/parser/htmlparser/src/nsScanner.cpp
index 93ce54eea57..938202153a5 100644
--- a/mozilla/parser/htmlparser/src/nsScanner.cpp
+++ b/mozilla/parser/htmlparser/src/nsScanner.cpp
@@ -31,8 +31,27 @@ const int kBufsize=64;
/**
- * Use this constructor if you want i/o to be based on an
- * incremental netstream. If you pass a null filename, you
+ * Use this constructor if you want i/o to be based on
+ * a single string you hand in during construction.
+ * This short cut was added for Javascript.
+ *
+ * @update gess 5/12/98
+ * @param aMode represents the parser mode (nav, other)
+ * @return
+ */
+CScanner::CScanner(nsString& anHTMLString) :
+ mBuffer(anHTMLString), mFilename("")
+{
+ mTotalRead=mBuffer.Length();
+ mIncremental=PR_FALSE;
+ mOwnsStream=PR_FALSE;
+ mOffset=0;
+ mFileStream=0;
+}
+
+/**
+ * Use this constructor if you want i/o to be based on strings
+ * the scanner receives. If you pass a null filename, you
* can still provide data to the scanner via append.
*
* @update gess 5/12/98
@@ -42,6 +61,7 @@ const int kBufsize=64;
CScanner::CScanner(nsString& aFilename,PRBool aCreateStream) :
mBuffer(""), mFilename(aFilename)
{
+ mIncremental=PR_TRUE;
mOffset=0;
mMarkPos=-1;
mTotalRead=0;
@@ -71,6 +91,7 @@ CScanner::CScanner(nsString& aFilename,PRBool aCreateStream) :
CScanner::CScanner(nsString& aFilename,fstream& aStream,PRBool assumeOwnership) :
mBuffer(""), mFilename(aFilename)
{
+ mIncremental=PR_TRUE;
mOffset=0;
mMarkPos=-1;
mTotalRead=0;
@@ -135,26 +156,17 @@ void _PreCompressBuffer(nsString& aBuffer,PRInt32& anOffset,PRInt32& aMarkPos){
//we've guaranteed the client we can back up to, so make sure
//you don't lose any of the data beyond that point.
-/*
- if((anOffset!=aMarkPos) && (0<=aMarkPos)) {
- if(aMarkPos>0) {
- aBuffer.Cut(0,aMarkPos);
- if(anOffset>aMarkPos)
- anOffset-=aMarkPos;
- }
- }
- else aBuffer.Truncate();
-*/
PRInt32 len=aBuffer.Length();
- if((aMarkPos=0)) {
+ if((aMarkPos0)) {
aBuffer.Cut(0,aMarkPos);
anOffset-=aMarkPos;
+ aMarkPos=0;
}
- else {
+ else if((anOffset==aMarkPos) && (0