]> git.tdb.fi Git - libs/datafile.git/commitdiff
Restructure control statement processing
authorMikko Rasa <tdb@tdb.fi>
Mon, 5 Aug 2013 09:19:31 +0000 (12:19 +0300)
committerMikko Rasa <tdb@tdb.fi>
Mon, 5 Aug 2013 11:57:46 +0000 (14:57 +0300)
Binary format control statements can no longer occur as substatements, but
that was an accidental feature at best.

source/binaryparser.cpp
source/binaryparser.h
source/parser.cpp
source/parser.h
source/parsermode.h
source/statement.h
source/textparser.cpp
source/textparser.h
tool/packer.cpp
tool/tool.cpp

index 7d1591de77105264a3d59fc2506c4bd0c03a9739..25edd63a15060d96bb5bcc95775cc3241dc9ce36 100644 (file)
@@ -32,45 +32,7 @@ BinaryParser::BinaryParser(Input &i, const string &s):
        dict[-3] = StatementKey("__flt", "i");
 }
 
-Statement BinaryParser::parse(bool raw)
-{
-       while(1)
-       {
-               Statement st = parse_statement(raw);
-               if(st.keyword=="__kwd")
-               {
-                       int id = st.args[0].get<int>();
-                       if(id<=0)
-                               throw bad_definition("__kwd");
-
-                       const string &kw = st.args[1].get<const string &>();
-                       const string &args = st.args[2].get<const string &>();
-                       for(string::const_iterator i=args.begin(); i!=args.end(); ++i)
-                               for(unsigned j=0; valid_signatures[j]!=*i; ++j)
-                                       if(!valid_signatures[j])
-                                               throw bad_definition("__kwd");
-
-                       dict[id] = StatementKey(kw, args);
-               }
-               else if(st.keyword=="__str")
-               {
-                       int id = st.args[0].get<int>();
-                       if(id<=0)
-                               throw bad_definition("__str");
-
-                       strings[id] = st.args[1].get<const string &>();
-               }
-               else if(st.keyword=="__flt")
-                       float_precision = st.args[0].get<unsigned>();
-               else
-                       return st;
-
-               if(raw)
-                       return st;
-       }
-}
-
-Statement BinaryParser::parse_statement(bool raw)
+Statement BinaryParser::parse()
 {
        while(first && in.peek()=='\n')
                in.get();
@@ -110,13 +72,42 @@ Statement BinaryParser::parse_statement(bool raw)
 
        unsigned nsub = parse_int();
        for(unsigned j = 0; j<nsub; ++j)
-               result.sub.push_back(parse(raw));
+               result.sub.push_back(parse());
 
        result.valid = true;
 
        return result;
 }
 
+void BinaryParser::process_control_statement(const Statement &st)
+{
+       if(st.keyword=="__kwd")
+       {
+               int id = st.args[0].get<int>();
+               if(id<=0)
+                       throw bad_definition("__kwd");
+
+               const string &kw = st.args[1].get<const string &>();
+               const string &args = st.args[2].get<const string &>();
+               for(string::const_iterator i=args.begin(); i!=args.end(); ++i)
+                       for(unsigned j=0; valid_signatures[j]!=*i; ++j)
+                               if(!valid_signatures[j])
+                                       throw bad_definition("__kwd");
+
+               dict[id] = StatementKey(kw, args);
+       }
+       else if(st.keyword=="__str")
+       {
+               int id = st.args[0].get<int>();
+               if(id<=0)
+                       throw bad_definition("__str");
+
+               strings[id] = st.args[1].get<const string &>();
+       }
+       else if(st.keyword=="__flt")
+               float_precision = st.args[0].get<unsigned>();
+}
+
 IntType::Store BinaryParser::parse_int()
 {
        IntType::Store result = 0;
index d275290cbece483a6b1ec1b2b6e109da9f5806db..6a46639cbbca7667873f5c5a68d30f8151e62dfa 100644 (file)
@@ -25,9 +25,9 @@ private:
 public:
        BinaryParser(Input &i, const std::string &s);
 
-       virtual Statement parse(bool);
+       virtual Statement parse();
+       virtual void process_control_statement(const Statement &);
 private:
-       Statement parse_statement(bool);
        IntType::Store parse_int();
        FloatType::Store parse_float();
        StringType::Store parse_string();
index 3957cf343642b54f2f5b6123be3e907bc200436e..6166e561a984a0d99878f313199003fac095039b 100644 (file)
@@ -32,37 +32,17 @@ Statement Parser::parse(bool raw)
        {
                while(1)
                {
-                       Statement st = mode->parse(raw);
-                       if(st.keyword=="__bin")
+                       Statement st = mode->parse();
+                       if(!st.keyword.compare(0, 2, "__"))
                        {
-                               delete mode;
-                               mode = new BinaryParser(in, src);
+                               st.control = true;
+                               process_control_statement(st);
                        }
-                       else if(st.keyword=="__text")
-                       {
-                               delete mode;
-                               mode = new TextParser(in, src);
-                       }
-                       else if(st.keyword=="__z")
-                               in.set_decompress();
-                       else if(st.keyword=="__src")
-                       {
-                               string s = st.args[0].get<string>();
-                               if(s.empty())
-                                       src = main_src;
-                               else
-                                       src = format("%s[%s]", main_src, s);
-                       }
-                       else if(st.keyword=="__end")
-                       {
-                               good = false;
-                               return raw ? st : Statement();
-                       }
-                       else
-                               return st;
 
-                       if(raw)
+                       if(raw || !st.control)
                                return st;
+                       else if(!good)  // This will occur with an __end statement
+                               return Statement();
                }
        }
        catch(const exception &e)
@@ -75,5 +55,33 @@ Statement Parser::parse(bool raw)
        }
 }
 
+void Parser::process_control_statement(const Statement &st)
+{
+       if(st.keyword=="__bin")
+       {
+               delete mode;
+               mode = new BinaryParser(in, src);
+       }
+       else if(st.keyword=="__text")
+       {
+               delete mode;
+               mode = new TextParser(in, src);
+       }
+       else if(st.keyword=="__z")
+               in.set_decompress();
+       else if(st.keyword=="__src")
+       {
+               string s = st.args[0].get<string>();
+               if(s.empty())
+                       src = main_src;
+               else
+                       src = format("%s[%s]", main_src, s);
+       }
+       else if(st.keyword=="__end")
+               good = false;
+       else
+               mode->process_control_statement(st);
+}
+
 } // namespace DataFile
 } // namespace Msp
index 6ad28b5b13c7a3824e3f05422834792cf758bccd..0989bd9d2d1fe378920c469c845f71435d799b28 100644 (file)
@@ -36,6 +36,10 @@ public:
        */
        Statement parse(bool raw = false);
 
+private:
+       void process_control_statement(const Statement &);
+
+public:
        operator bool() const { return good && in; }
 };
 
index 58a7e27de1704a2ab0aee90aa13a5b14c0145a0a..620e9a91acb7f325535b6b0c87fe30545d409cc1 100644 (file)
@@ -21,7 +21,8 @@ protected:
 public:
        virtual ~ParserMode() { }
 
-       virtual Statement parse(bool) = 0;
+       virtual Statement parse() = 0;
+       virtual void process_control_statement(const Statement &) { }
 };
 
 } // namespace DataFile
index 1df34381b38630b97494764e5e6c2fd581c0723a..80b7b15af8da82566f3526d1494e82a3a787c2e4 100644 (file)
@@ -15,6 +15,7 @@ public:
        std::string keyword;
        Arguments args;
        bool valid;
+       bool control;
        std::string source;
        unsigned line;
        std::list<Statement> sub;
index afa78b99927ddb67c581f47484b9cefc1c567a7e..05521a90456a617e2e82b1fb664225d512a22af4 100644 (file)
@@ -35,7 +35,7 @@ TextParser::TextParser(Input &i, const string &s):
        ParserMode(i, s)
 { }
 
-Statement TextParser::parse(bool)
+Statement TextParser::parse()
 {
        return parse_statement(0);
 }
index 8235dc6addde9143dc4a3327f5a07554f01ceab7..e8c89227ddc7300b7e745faca33a3f08c0089b8b 100644 (file)
@@ -13,7 +13,7 @@ class TextParser: public ParserMode
 public:
        TextParser(Input &, const std::string &);
 
-       virtual Statement parse(bool);
+       virtual Statement parse();
 protected:
        Statement parse_statement(const Token *);
        Token parse_token();
index 44be7243e86e45df093e8fdf38270f8bcdfbbd45..ff69912fe40124fe4d64e37f5d13330b521782c0 100644 (file)
@@ -106,8 +106,7 @@ void Packer::transfer_datafile(IO::Base &in, const string &fn, IO::Base &out, Ob
                DataFile::Statement st = parser.parse(true);
                if(st.valid)
                {
-                       bool sys = !st.keyword.compare(0, 2, "__");
-                       if(collection && !sys)
+                       if(collection && !st.control)
                        {
                                if(st.get_signature()=="s")
                                {
@@ -119,7 +118,7 @@ void Packer::transfer_datafile(IO::Base &in, const string &fn, IO::Base &out, Ob
                                else
                                        collection = false;
                        }
-                       if(!sys || st.keyword=="__src")
+                       if(!st.control || st.keyword=="__src")
                                writer->write(st);
                }
        }
index 81c6be9b831b8bd74a80258337cd5d692f0d4734..a82d5875f2a40630cfc1252f5a99ac920bdfc60c 100644 (file)
@@ -63,7 +63,7 @@ void DataTool::do_transfer()
                while(parser)
                {
                        DataFile::Statement st = parser.parse(true);
-                       if(st.valid && (st.keyword.compare(0, 2, "__") || st.keyword=="__src" || debug))
+                       if(st.valid && (!st.control || st.keyword=="__src" || debug))
                                writer->write(st);
                }