Fixed a crash when opening broken xml file

This commit is contained in:
Deve 2018-11-22 22:09:05 +01:00
parent 7a2ae14d7c
commit cdb3d2cae5

View File

@ -225,7 +225,7 @@ private:
char_type* start = P; char_type* start = P;
// more forward until '<' found // more forward until '<' found
while(*P != L'<' && *P) while(*P && *P != L'<')
++P; ++P;
// not a node, so return false // not a node, so return false
@ -239,7 +239,8 @@ private:
return true; return true;
} }
++P; if (*P)
++P;
// based on current token, parse and report next element // based on current token, parse and report next element
switch(*P) switch(*P)
@ -297,10 +298,11 @@ private:
CurrentNodeType = EXN_UNKNOWN; CurrentNodeType = EXN_UNKNOWN;
// move until end marked with '>' reached // move until end marked with '>' reached
while(*P != L'>') while(*P && *P != L'>')
++P; ++P;
++P; if (*P)
++P;
} }
@ -308,14 +310,15 @@ private:
void parseComment() void parseComment()
{ {
CurrentNodeType = EXN_COMMENT; CurrentNodeType = EXN_COMMENT;
P += 1; if (*P)
P += 1;
char_type *pCommentBegin = P; char_type *pCommentBegin = P;
int count = 1; int count = 1;
// move until end of comment reached // move until end of comment reached
while(count) while(*P && count)
{ {
if (*P == L'>') if (*P == L'>')
--count; --count;
@ -326,9 +329,16 @@ private:
++P; ++P;
} }
P -= 3; if (*P)
NodeName = core::string<char_type>(pCommentBegin+2, (int)(P - pCommentBegin-2)); {
P += 3; P -= 3;
NodeName = core::string<char_type>(pCommentBegin+2, (int)(P - pCommentBegin-2));
P += 3;
}
else
{
NodeName = "";
}
} }
@ -343,13 +353,13 @@ private:
const char_type* startName = P; const char_type* startName = P;
// find end of element // find end of element
while(*P != L'>' && !isWhiteSpace(*P)) while(*P && *P != L'>' && !isWhiteSpace(*P))
++P; ++P;
const char_type* endName = P; const char_type* endName = P;
// find Attributes // find Attributes
while(*P != L'>') while(*P && *P != L'>')
{ {
if (isWhiteSpace(*P)) if (isWhiteSpace(*P))
++P; ++P;
@ -362,15 +372,16 @@ private:
// read the attribute names // read the attribute names
const char_type* attributeNameBegin = P; const char_type* attributeNameBegin = P;
while(!isWhiteSpace(*P) && *P != L'=') while(*P && !isWhiteSpace(*P) && *P != L'=')
++P; ++P;
const char_type* attributeNameEnd = P; const char_type* attributeNameEnd = P;
++P; if (*P)
++P;
// read the attribute value // read the attribute value
// check for quotes and single quotes, thx to murphy // check for quotes and single quotes, thx to murphy
while( (*P != L'\"') && (*P != L'\'') && *P) while(*P && (*P != L'\"') && (*P != L'\''))
++P; ++P;
if (!*P) // malformatted xml file if (!*P) // malformatted xml file
@ -378,17 +389,19 @@ private:
const char_type attributeQuoteChar = *P; const char_type attributeQuoteChar = *P;
++P; if (*P)
++P;
const char_type* attributeValueBegin = P; const char_type* attributeValueBegin = P;
while(*P != attributeQuoteChar && *P) while(*P && *P != attributeQuoteChar)
++P; ++P;
if (!*P) // malformatted xml file if (!*P) // malformatted xml file
return; return;
const char_type* attributeValueEnd = P; const char_type* attributeValueEnd = P;
++P; if (*P)
++P;
SAttribute attr; SAttribute attr;
attr.Name = core::string<char_type>(attributeNameBegin, attr.Name = core::string<char_type>(attributeNameBegin,
@ -403,7 +416,8 @@ private:
else else
{ {
// tag is closed directly // tag is closed directly
++P; if (*P)
++P;
IsEmptyElement = true; IsEmptyElement = true;
break; break;
} }
@ -420,7 +434,8 @@ private:
NodeName = core::string<char_type>(startName, (int)(endName - startName)); NodeName = core::string<char_type>(startName, (int)(endName - startName));
++P; if (*P)
++P;
} }
@ -431,20 +446,23 @@ private:
IsEmptyElement = false; IsEmptyElement = false;
Attributes.clear(); Attributes.clear();
++P; if (*P)
++P;
const char_type* pBeginClose = P; const char_type* pBeginClose = P;
while(*P != L'>') while(*P && *P != L'>')
++P; ++P;
NodeName = core::string<char_type>(pBeginClose, (int)(P - pBeginClose)); NodeName = core::string<char_type>(pBeginClose, (int)(P - pBeginClose));
++P;
if (*P)
++P;
} }
//! parses a possible CDATA section, returns false if begin was not a CDATA section //! parses a possible CDATA section, returns false if begin was not a CDATA section
bool parseCDATA() bool parseCDATA()
{ {
if (*(P+1) != L'[') if (!*P || !*(P+1) || *(P+1) != L'[')
return false; return false;
CurrentNodeType = EXN_CDATA; CurrentNodeType = EXN_CDATA;