aeae1cb7c6
[SVN r56670]
187 lines
5.0 KiB
C++
187 lines
5.0 KiB
C++
// Copyright (c) 2005 Carl Barron. Distributed under the Boost
|
|
// Software License, Version 1.0. (See accompanying file
|
|
// LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
|
|
|
#ifndef XML_G_H
|
|
#define XML_G_H
|
|
#define BOOST_SPIRIT_DEBUG
|
|
#ifndef BOOST_SPIRIT_CLOSURE_LIMIT
|
|
#define BOOST_SPIRIT_CLOSURE_LIMIT 10
|
|
#endif
|
|
|
|
#ifndef PHOENIX_LIMIT
|
|
#define PHOENIX_LIMIT 10
|
|
#endif
|
|
|
|
#if BOOST_SPIRIT_CLOSURE_LIMIT < 6
|
|
#undef BOOST_SPIRIT_CLOSURE_LIMIT
|
|
#define BOOST_SPIRIT_CLOSURE_LIMIT 6
|
|
#endif
|
|
|
|
#if PHOENIX_LIMIT < BOOST_SPIRIT_CLOSURE_LIMIT
|
|
#undef PHOENIX_LIMIT
|
|
#define PHOENIX_LIMIT BOOST_SPIRIT_CLOSURE_LIMIT
|
|
#endif
|
|
|
|
#if 0
|
|
#ifdef BOOST_SPIRIT_DEBUG_FLAGS
|
|
#undef BOOST_SPIRIT_DEBUG_FLAGS
|
|
#endif
|
|
#define BOOST_SPIRIT_DEBUG_FLAGS (BOOST_SPIRIT_DEBUG_FLAGS_MAX - BOOST_SPIRIT_DEBUG_FLAGS_CLOSURES)
|
|
#endif
|
|
|
|
#include <boost/spirit/include/classic_core.hpp>
|
|
#include <boost/spirit/include/classic_attribute.hpp>
|
|
#include <boost/spirit/include/phoenix1.hpp>
|
|
#include "tag.hpp"
|
|
#include "actions.hpp"
|
|
#include <boost/variant.hpp>
|
|
|
|
#include <string>
|
|
#include <utility>
|
|
|
|
namespace SP = BOOST_SPIRIT_CLASSIC_NS;
|
|
using phoenix::arg1;
|
|
using phoenix::arg2;
|
|
using phoenix::construct_;
|
|
using phoenix::var;
|
|
|
|
struct str_cls:SP::closure<str_cls,std::string>
|
|
{ member1 value;};
|
|
|
|
struct attrib_cls:SP::closure
|
|
<
|
|
attrib_cls,
|
|
std::pair<std::string,std::string>,
|
|
std::string,
|
|
std::string
|
|
>
|
|
{
|
|
member1 value;
|
|
member2 first;
|
|
member3 second;
|
|
};
|
|
|
|
struct tagged_cls:SP::closure
|
|
<
|
|
tagged_cls,
|
|
tag,
|
|
std::string,
|
|
std::map<std::string,std::string>,
|
|
std::list<typename tag::variant_type>
|
|
>
|
|
{
|
|
member1 value;
|
|
member2 ID;
|
|
member3 attribs;
|
|
member4 children;
|
|
};
|
|
|
|
struct xml_g:SP::grammar<xml_g>
|
|
{
|
|
std::list<tag> &tags;
|
|
xml_g(std::list<tag> &a):tags(a){}
|
|
template <class Scan>
|
|
struct definition
|
|
{
|
|
definition(const xml_g &s)
|
|
{
|
|
white = +SP::space_p
|
|
;
|
|
|
|
tagged = (start_tag
|
|
>> *inner
|
|
>> end_tag
|
|
| simple_start_tag
|
|
)
|
|
[store_tag(tagged.value,tagged.ID,tagged.attribs,
|
|
tagged.children)]
|
|
;
|
|
|
|
end_tag = SP::str_p("</")
|
|
>> SP::f_str_p(tagged.ID)
|
|
>> '>'
|
|
;
|
|
|
|
inner = (tagged
|
|
| str) [push_child(tagged.children,arg1)]
|
|
;
|
|
|
|
str = SP::lexeme_d[+(SP::anychar_p - '<')]
|
|
[str.value=construct_<std::string>(arg1,arg2)]
|
|
;
|
|
|
|
top = +tagged
|
|
[push_back(var(s.tags),arg1)]
|
|
;
|
|
|
|
starter = SP::ch_p('<')
|
|
>> SP::lexeme_d[+SP::alpha_p]
|
|
[tagged.ID = construct_<std::string>(arg1,arg2)]
|
|
>> *attrib
|
|
[store_in_map(tagged.attribs,arg1)]
|
|
>> !white
|
|
;
|
|
start_tag = starter
|
|
>> '>'
|
|
;
|
|
|
|
simple_start_tag = starter
|
|
>> "/>"
|
|
;
|
|
|
|
attrib = white
|
|
>>SP::lexeme_d[+SP::alpha_p]
|
|
[attrib.first = construct_<std::string>(arg1,arg2)]
|
|
>> !white
|
|
>> '='
|
|
>> !white
|
|
>> '"'
|
|
>> SP::lexeme_d[+(SP::anychar_p - '"')]
|
|
[attrib.second = construct_<std::string>(arg1,arg2)]
|
|
>> SP::ch_p('"')
|
|
[attrib.value = construct_
|
|
<
|
|
std::pair
|
|
<
|
|
std::string,
|
|
std::string
|
|
>
|
|
>(attrib.first,attrib.second)]
|
|
;
|
|
BOOST_SPIRIT_DEBUG_RULE(tagged);
|
|
BOOST_SPIRIT_DEBUG_RULE(end_tag);
|
|
BOOST_SPIRIT_DEBUG_RULE(inner);
|
|
BOOST_SPIRIT_DEBUG_RULE(str);
|
|
BOOST_SPIRIT_DEBUG_RULE(top);
|
|
BOOST_SPIRIT_DEBUG_RULE(start_tag);
|
|
BOOST_SPIRIT_DEBUG_RULE(attrib);
|
|
BOOST_SPIRIT_DEBUG_RULE(white);
|
|
BOOST_SPIRIT_DEBUG_RULE(starter);
|
|
BOOST_SPIRIT_DEBUG_RULE(simple_start_tag);
|
|
}
|
|
|
|
// actions
|
|
push_back_f push_back;
|
|
push_child_f push_child;
|
|
store_in_map_f store_in_map;
|
|
store_tag_f store_tag;
|
|
// rules
|
|
SP::rule<Scan,tagged_cls::context_t> tagged;
|
|
SP::rule<Scan> end_tag;
|
|
SP::rule<Scan> inner;
|
|
SP::rule<Scan,str_cls::context_t> str;
|
|
SP::rule<Scan> top;
|
|
SP::rule<Scan> starter;
|
|
SP::rule<Scan> simple_start_tag;
|
|
SP::rule<Scan> start_tag;
|
|
SP::rule<Scan> white;
|
|
SP::rule<Scan,attrib_cls::context_t> attrib;
|
|
SP::rule<Scan> const &start() const
|
|
{ return top;}
|
|
};
|
|
};
|
|
|
|
#endif
|
|
|