Skip to content
Snippets Groups Projects
Commit a9897ea6 authored by Rye Mutt's avatar Rye Mutt :bread:
Browse files

LLSDXml parsing improvements inspired by NickyD

parent d5a20f55
No related branches found
No related tags found
No related merge requests found
...@@ -29,6 +29,7 @@ ...@@ -29,6 +29,7 @@
#include <iostream> #include <iostream>
#include <deque> #include <deque>
#include <stack>
#include "apr_base64.h" #include "apr_base64.h"
...@@ -220,6 +221,13 @@ std::string LLSDXMLFormatter::escapeString(const std::string& in) ...@@ -220,6 +221,13 @@ std::string LLSDXMLFormatter::escapeString(const std::string& in)
std::string::const_iterator end = in.end(); std::string::const_iterator end = in.end();
for(; it != end; ++it) for(; it != end; ++it)
{ {
// See http://en.wikipedia.org/wiki/Valid_characters_in_XML
if( *it >= 0 && *it < 20 && *it != 0x09 && *it != 0x0A && *it != 0x0D )
{
out << "?";
continue;
}
switch((*it)) switch((*it))
{ {
case '<': case '<':
...@@ -304,8 +312,9 @@ class LLSDXMLParser::Impl ...@@ -304,8 +312,9 @@ class LLSDXMLParser::Impl
bool mInLLSDElement; // true if we're on LLSD bool mInLLSDElement; // true if we're on LLSD
bool mGracefullStop; // true if we found the </llsd bool mGracefullStop; // true if we found the </llsd
typedef std::deque<LLSD*> LLSDRefStack; typedef std::vector<LLSD*> LLSDRefStack;
LLSDRefStack mStack; LLSDRefStack mStack;
std::vector<Element> mStackElements;
int mDepth; int mDepth;
bool mSkipping; bool mSkipping;
...@@ -506,7 +515,8 @@ void LLSDXMLParser::Impl::reset() ...@@ -506,7 +515,8 @@ void LLSDXMLParser::Impl::reset()
mGracefullStop = false; mGracefullStop = false;
mStack.clear(); mStack.clear();
mStackElements.clear();
mSkipping = false; mSkipping = false;
mCurrentKey.clear(); mCurrentKey.clear();
...@@ -593,19 +603,24 @@ void LLSDXMLParser::Impl::startElementHandler(const XML_Char* name, const XML_Ch ...@@ -593,19 +603,24 @@ void LLSDXMLParser::Impl::startElementHandler(const XML_Char* name, const XML_Ch
} }
Element element = readElement(name); Element element = readElement(name);
mStackElements.push_back(element);
mCurrentContent.clear(); mCurrentContent.clear();
switch (element) switch (element)
{ {
case ELEMENT_LLSD: case ELEMENT_LLSD:
if (mInLLSDElement) { return startSkipping(); } if (mInLLSDElement)
{
mStackElements.pop_back();
return startSkipping();
}
mInLLSDElement = true; mInLLSDElement = true;
return; return;
case ELEMENT_KEY: case ELEMENT_KEY:
if (mStack.empty() || !(mStack.back()->isMap())) if (mStack.empty() || !(mStack.back()->isMap()))
{ {
mStackElements.pop_back();
return startSkipping(); return startSkipping();
} }
return; return;
...@@ -613,7 +628,11 @@ void LLSDXMLParser::Impl::startElementHandler(const XML_Char* name, const XML_Ch ...@@ -613,7 +628,11 @@ void LLSDXMLParser::Impl::startElementHandler(const XML_Char* name, const XML_Ch
case ELEMENT_BINARY: case ELEMENT_BINARY:
{ {
const XML_Char* encoding = findAttribute("encoding", attributes); const XML_Char* encoding = findAttribute("encoding", attributes);
if(encoding && strcmp("base64", encoding) != 0) { return startSkipping(); } if(encoding && strcmp("base64", encoding) != 0)
{
mStackElements.pop_back();
return startSkipping();
}
break; break;
} }
...@@ -623,7 +642,11 @@ void LLSDXMLParser::Impl::startElementHandler(const XML_Char* name, const XML_Ch ...@@ -623,7 +642,11 @@ void LLSDXMLParser::Impl::startElementHandler(const XML_Char* name, const XML_Ch
} }
if (!mInLLSDElement) { return startSkipping(); } if (!mInLLSDElement)
{
mStackElements.pop_back();
return startSkipping();
}
if (mStack.empty()) if (mStack.empty())
{ {
...@@ -631,7 +654,11 @@ void LLSDXMLParser::Impl::startElementHandler(const XML_Char* name, const XML_Ch ...@@ -631,7 +654,11 @@ void LLSDXMLParser::Impl::startElementHandler(const XML_Char* name, const XML_Ch
} }
else if (mStack.back()->isMap()) else if (mStack.back()->isMap())
{ {
if (mCurrentKey.empty()) { return startSkipping(); } if (mCurrentKey.empty())
{
mStackElements.pop_back();
return startSkipping();
}
LLSD& map = *mStack.back(); LLSD& map = *mStack.back();
LLSD& newElement = map[mCurrentKey]; LLSD& newElement = map[mCurrentKey];
...@@ -648,6 +675,7 @@ void LLSDXMLParser::Impl::startElementHandler(const XML_Char* name, const XML_Ch ...@@ -648,6 +675,7 @@ void LLSDXMLParser::Impl::startElementHandler(const XML_Char* name, const XML_Ch
} }
else { else {
// improperly nested value in a non-structure // improperly nested value in a non-structure
mStackElements.pop_back();
return startSkipping(); return startSkipping();
} }
...@@ -684,8 +712,9 @@ void LLSDXMLParser::Impl::endElementHandler(const XML_Char* name) ...@@ -684,8 +712,9 @@ void LLSDXMLParser::Impl::endElementHandler(const XML_Char* name)
return; return;
} }
Element element = readElement(name); Element element = mStackElements.back(); //readElement(name);
mStackElements.pop_back();
switch (element) switch (element)
{ {
case ELEMENT_LLSD: case ELEMENT_LLSD:
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment