]> granicus.if.org Git - re2c/commitdiff
Removed variable from global scope, simplified bitmaps.
authorUlya Trofimovich <skvadrik@gmail.com>
Mon, 19 Dec 2016 00:06:19 +0000 (00:06 +0000)
committerUlya Trofimovich <skvadrik@gmail.com>
Mon, 19 Dec 2016 00:06:19 +0000 (00:06 +0000)
12 files changed:
re2c/src/codegen/bitmap.cc
re2c/src/codegen/bitmap.h
re2c/src/codegen/emit_dfa.cc
re2c/src/codegen/go.h
re2c/src/codegen/go_construct.cc
re2c/src/globals.h
re2c/src/ir/adfa/adfa.cc
re2c/src/ir/adfa/adfa.h
re2c/src/ir/adfa/prepare.cc
re2c/src/ir/skeleton/generate_code.cc
re2c/src/ir/skeleton/skeleton.h
re2c/src/main.cc

index 16a0668b2cf78e5909856a61efb417fabd5ebaec..645216752327c953b2b9cde2aa23ca3ea176f659 100644 (file)
@@ -9,50 +9,83 @@
 namespace re2c
 {
 
-BitMap *BitMap::first = NULL;
-
-BitMap::BitMap(const Go *g, const State *x)
-       : go(g)
-       , on(x)
-       , next(first)
-       , i(0)
-       , m(0)
+static bool matches(const Go *go1, const State *s1, const Go *go2, const State *s2);
+static void doGen(const Go *g, const State *s, uint32_t *bm, uint32_t f, uint32_t m);
+
+bitmaps_t::bitmaps_t(uint32_t n)
+       : maps()
+       , ncunit(n)
+       , buffer(new uint32_t[ncunit])
+       , used(false)
+{}
+
+bitmaps_t::~bitmaps_t()
 {
-       first = this;
+       delete[] buffer;
 }
 
-BitMap::~BitMap()
+void bitmaps_t::insert(const Go *go, const State *s)
 {
-       delete next;
+       for (rciter_t i = maps.rbegin(); i != maps.rend(); ++i) {
+               if (matches(i->go, i->on, go, s)) return;
+       }
+
+       bitmap_t b = {go, s, 0, 0};
+       maps.push_back(b);
 }
 
-const BitMap *BitMap::find(const Go *g, const State *x)
+const bitmap_t *bitmaps_t::find(const Go *go, const State *s) const
 {
-       for (const BitMap *b = first; b; b = b->next)
-       {
-               if (matches(b->go->span, b->go->nSpans, b->on, g->span, g->nSpans, x))
-               {
-                       return b;
-               }
+       for (rciter_t i = maps.rbegin(); i != maps.rend(); ++i) {
+               if (i->on == s && matches(i->go, i->on, go, s)) return &(*i);
        }
-
-       return new BitMap(g, x);
+       return NULL;
 }
 
-const BitMap *BitMap::find(const State *x)
+bool bitmaps_t::empty() const { return maps.empty(); }
+
+void bitmaps_t::gen(OutputFile &o, uint32_t ind)
 {
-       for (const BitMap *b = first; b; b = b->next)
-       {
-               if (b->on == x)
-               {
-                       return b;
+       if (empty() || !used) return;
+
+       Opt &opts = o.opts;
+       const uint32_t nmap = static_cast<uint32_t>(maps.size());
+       riter_t b = maps.rbegin(), e = maps.rend();
+
+       o.wind(ind).ws("static const unsigned char ")
+               .wstring(opts->yybm).ws("[] = {");
+
+       for (uint32_t i = 0, t = 1; b != e; i += ncunit, t += 8) {
+               memset(buffer, 0, ncunit * sizeof(uint32_t));
+
+               for (uint32_t m = 0x80; b != e && m; m >>= 1, ++b) {
+                       b->i = i;
+                       b->m = m;
+                       doGen(b->go, b->on, buffer, 0, m);
+               }
+
+               if (nmap > 8) {
+                       o.ws("\n").wind(ind + 1).ws("/* table ").wu32(t).ws(" .. ")
+                               .wu32(std::min(nmap, t + 7)).ws(": ").wu32(i).ws(" */");
+               }
+
+               for (uint32_t c = 0; c < ncunit; ++c) {
+                       if (c % 8 == 0) {
+                               o.ws("\n").wind(ind + 1);
+                       }
+                       if (opts->yybmHexTable) {
+                               o.wu32_hex(buffer[c]);
+                       } else {
+                               o.wu32_width(buffer[c], 3);
+                       }
+                       o.ws(", ");
                }
        }
 
-       return NULL;
+       o.ws("\n").wind(ind).ws("};\n");
 }
 
-static void doGen(const Go *g, const State *s, uint32_t *bm, uint32_t f, uint32_t m)
+void doGen(const Go *g, const State *s, uint32_t *bm, uint32_t f, uint32_t m)
 {
        Span *b = g->span, *e = &b[g->nSpans];
        uint32_t lb = 0;
@@ -71,72 +104,13 @@ static void doGen(const Go *g, const State *s, uint32_t *bm, uint32_t f, uint32_
        }
 }
 
-void BitMap::gen(OutputFile & o, uint32_t ind, uint32_t lb, uint32_t ub)
-{
-       Opt &opts = o.opts;
-       if (first && bUsedYYBitmap)
-       {
-               o.wind(ind).ws("static const unsigned char ").wstring(opts->yybm).ws("[] = {");
-
-               uint32_t c = 1, n = ub - lb;
-               const BitMap *cb = first;
-
-               while((cb = cb->next) != NULL) {
-                       ++c;
-               }
-               BitMap *b = first;
-
-               uint32_t *bm = new uint32_t[n];
-               
-               for (uint32_t i = 0, t = 1; b; i += n, t += 8)
-               {
-                       memset(bm, 0, n * sizeof(uint32_t));
-
-                       for (uint32_t m = 0x80; b && m; m >>= 1)
-                       {
-                               b->i = i;
-                               b->m = m;
-                               doGen(b->go, b->on, bm, lb, m);
-                               b = const_cast<BitMap*>(b->next);
-                       }
-
-                       if (c > 8)
-                       {
-                               o.ws("\n").wind(ind+1).ws("/* table ").wu32(t).ws(" .. ").wu32(std::min(c, t+7)).ws(": ").wu32(i).ws(" */");
-                       }
-
-                       for (uint32_t j = 0; j < n; ++j)
-                       {
-                               if (j % 8 == 0)
-                               {
-                                       o.ws("\n").wind(ind+1);
-                               }
-
-                               if (opts->yybmHexTable)
-                               {
-                                       o.wu32_hex(bm[j]);
-                               }
-                               else
-                               {
-                                       o.wu32_width(bm[j], 3);
-                               }
-                               o.ws(", ");
-                       }
-               }
-
-               o.ws("\n").wind(ind).ws("};\n");
-               
-               delete[] bm;
-       }
-}
-
 // All spans in b1 that lead to s1 are pairwise equal to that in b2 leading to s2
-bool matches(const Span * b1, uint32_t n1, const State * s1, const Span * b2, uint32_t n2, const State * s2)
+bool matches(const Go *go1, const State *s1, const Go *go2, const State *s2)
 {
-       const Span * e1 = &b1[n1];
-       uint32_t lb1 = 0;
-       const Span * e2 = &b2[n2];
-       uint32_t lb2 = 0;
+       const Span
+               *b1 = go1->span, *e1 = &b1[go1->nSpans],
+               *b2 = go2->span, *e2 = &b2[go2->nSpans];
+       uint32_t lb1 = 0, lb2 = 0;
 
        for (;;)
        {
index 3c0cc1be6245da8c25e580c65cf6f5bdbc40a162..a2f75abf4a71cbcdf536b1a81495079cb6f3aad5 100644 (file)
@@ -2,44 +2,47 @@
 #define _RE2C_CODEGEN_BITMAP_
 
 #include "src/util/c99_stdint.h"
+#include <vector>
 
 #include "src/util/forbid_copy.h"
 
-namespace re2c
-{
+namespace re2c {
 
 struct Go;
 struct Span;
 class State;
 class OutputFile;
 
-class BitMap
+struct bitmap_t
 {
-public:
-       static BitMap   *first;
+       const Go *go;
+       const State *on;
+       uint32_t i;
+       uint32_t m;
+};
+
+class bitmaps_t
+{
+       typedef std::vector<bitmap_t> maps_t;
+       typedef maps_t::reverse_iterator riter_t;
+       typedef maps_t::const_reverse_iterator rciter_t;
 
-       const Go        *go;
-       const State     *on;
-       const BitMap    *next;
-       uint32_t        i;
-       uint32_t        m;
+       maps_t maps;
+       uint32_t ncunit;
+       uint32_t *buffer;
 
 public:
-       static const BitMap *find(const Go*, const State*);
-       static const BitMap *find(const State*);
-       static void gen(OutputFile &, uint32_t ind, uint32_t, uint32_t);
-       BitMap(const Go*, const State*);
-       ~BitMap();
-
-       FORBID_COPY (BitMap);
+       bool used;
+
+       explicit bitmaps_t(uint32_t n);
+       ~bitmaps_t();
+       void insert(const Go *go, const State *s);
+       const bitmap_t *find(const Go *go, const State *s) const;
+       bool empty() const;
+       void gen(OutputFile &o, uint32_t ind);
+       FORBID_COPY(bitmaps_t);
 };
 
-bool matches(const Span * b1, uint32_t n1, const State * s1, const Span * b2, uint32_t n2, const State * s2);
-
-#ifdef _MSC_VER
-# pragma warning(disable: 4355) /* 'this' : used in base member initializer list */
-#endif
-
-} // end namespace re2c
+} // namespace re2c
 
 #endif // _RE2C_CODEGEN_BITMAP_
index 8350a7ae0c42ebcb5bef954bf9a44cfd508bc1db..8cef48e13d9151d2394c32314921624d88021aab 100644 (file)
@@ -187,7 +187,7 @@ void DFA::emit(Output & output, uint32_t& ind, bool isLastCond, bool& bPrologBra
                if (output.skeletons.insert (name).second)
                {
                        emit_start(o, max_fill, name, key_size, def_rule, need_backup,
-                               need_accept, oldstyle_ctxmarker, tagnames, tagvars);
+                               need_accept, oldstyle_ctxmarker, tagnames, tagvars, bitmaps);
                        uint32_t i = 2;
                        emit_body (o, i, used_labels, initial_label);
                        emit_end(o, name, need_backup, oldstyle_ctxmarker);
@@ -201,7 +201,7 @@ void DFA::emit(Output & output, uint32_t& ind, bool isLastCond, bool& bPrologBra
                        o.ws("\n").wdelay_line_info ();
                        if ((!opts->fFlag && ob.used_yyaccept)
                        ||  (!opts->fFlag && opts->bEmitYYCh)
-                       ||  (opts->bFlag && !opts->cFlag && BitMap::first)
+                       ||  (opts->bFlag && !opts->cFlag && !bitmaps.empty())
                        ||  (opts->cFlag && !bWroteCondCheck && opts->gFlag)
                        ||  (opts->fFlag && !bWroteGetState && opts->gFlag)
                        )
@@ -226,9 +226,9 @@ void DFA::emit(Output & output, uint32_t& ind, bool isLastCond, bool& bPrologBra
                                o.ws("\n");
                        }
                }
-               if (opts->bFlag && !opts->cFlag && BitMap::first)
+               if (opts->bFlag && !opts->cFlag)
                {
-                       BitMap::gen(o, ind, lbChar, ubChar <= 256 ? ubChar : 256);
+                       bitmaps.gen(o, ind);
                }
                if (bProlog)
                {
@@ -260,14 +260,14 @@ void DFA::emit(Output & output, uint32_t& ind, bool isLastCond, bool& bPrologBra
                        }
                        o.wstring(opts->condPrefix).wstring(cond).ws(":\n");
                }
-               if (opts->cFlag && opts->bFlag && BitMap::first)
+               if (opts->cFlag && opts->bFlag && !bitmaps.empty())
                {
                        o.wind(ind++).ws("{\n");
-                       BitMap::gen(o, ind, lbChar, ubChar <= 256 ? ubChar : 256);
+                       bitmaps.gen(o, ind);
                }
                // Generate code
                emit_body (o, ind, used_labels, initial_label);
-               if (opts->cFlag && opts->bFlag && BitMap::first)
+               if (opts->cFlag && opts->bFlag && !bitmaps.empty())
                {
                        o.wind(--ind).ws("}\n");
                }
@@ -277,13 +277,6 @@ void DFA::emit(Output & output, uint32_t& ind, bool isLastCond, bool& bPrologBra
                        o.wind(--ind).ws("}\n");
                }
        }
-
-       // Cleanup
-       if (BitMap::first)
-       {
-               delete BitMap::first;
-               BitMap::first = NULL;
-       }
 }
 
 void genCondTable(OutputFile & o, uint32_t ind, const std::vector<std::string> & condnames)
index b0d5fbeca1197a3a36f8adc7e444e35164918ccf..fa99ce2614cba452012862075ddc06a75497f547 100644 (file)
@@ -14,7 +14,8 @@ namespace re2c
 {
 
 struct DFA;
-class BitMap;
+class bitmap_t;
+class bitmaps_t;
 class State;
 struct If;
 
@@ -137,12 +138,12 @@ struct SwitchIf
 
 struct GoBitmap
 {
-       const BitMap * bitmap;
+       const bitmap_t * bitmap;
        const State * bitmap_state;
        SwitchIf * hgo;
        SwitchIf * lgo;
        GoBitmap (const Span * span, uint32_t nSpans, const Span * hspan,
-               uint32_t hSpans, const BitMap * bm, const State * bm_state,
+               uint32_t hSpans, const bitmap_t * bm, const State * bm_state,
                const State * next, bool sflag);
        ~GoBitmap ();
        void emit (OutputFile & o, uint32_t ind, const DFA &dfa);
@@ -213,7 +214,7 @@ struct Go
 
        Go ();
        ~Go ();
-       void init (const State * from, Opt &opts);
+       void init(const State* from, Opt &opts, bitmaps_t &bitmaps);
        void emit (OutputFile & o, uint32_t ind, const DFA &dfa);
        void used_labels (std::set<label_t> & used);
 
index 47fd4a76ca3dc0b746d780324b4f7a258d38f18f..2c056cbc65ac3403341cfeac56bc943218ab5d05 100644 (file)
@@ -139,7 +139,7 @@ SwitchIf::SwitchIf (const Span * sp, uint32_t nsp, const State * next, bool sfla
 }
 
 GoBitmap::GoBitmap (const Span * span, uint32_t nSpans, const Span * hspan,
-       uint32_t hSpans, const BitMap * bm, const State * bm_state,
+       uint32_t hSpans, const bitmap_t * bm, const State * bm_state,
        const State * next, bool sflag)
        : bitmap (bm)
        , bitmap_state (bm_state)
@@ -193,7 +193,7 @@ Go::Go ()
        , info ()
 {}
 
-void Go::init (const State * from, Opt &opts)
+void Go::init (const State * from, Opt &opts, bitmaps_t &bitmaps)
 {
        if (nSpans == 0)
        {
@@ -223,22 +223,20 @@ void Go::init (const State * from, Opt &opts)
 
        // initialize bitmaps
        uint32_t nBitmaps = 0;
-       const BitMap * bitmap = NULL;
-       const State * bitmap_state = NULL;
-       for (uint32_t i = 0; i < nSpans; ++i)
-       {
-               if (span[i].to->isBase)
-               {
-                       const BitMap *b = BitMap::find (span[i].to);
-                       if (b && matches(b->go->span, b->go->nSpans, b->on, span, nSpans, span[i].to))
-                       {
-                               if (bitmap == NULL)
-                               {
-                                       bitmap = b;
-                                       bitmap_state = span[i].to;
-                               }
-                               nBitmaps++;
+       const bitmap_t *bm = NULL;
+       const State *bms = NULL;
+
+       for (uint32_t i = 0; i < nSpans; ++i) {
+               const State *s = span[i].to;
+               if (!s->isBase) continue;
+
+               const bitmap_t *b = bitmaps.find(this, s);
+               if (b) {
+                       if (bm == NULL) {
+                               bm = b;
+                               bms = s;
                        }
+                       ++nBitmaps;
                }
        }
 
@@ -256,8 +254,8 @@ void Go::init (const State * from, Opt &opts)
        else if (opts->bFlag && (nBitmaps > 0))
        {
                type = BITMAP;
-               info.bitmap = new GoBitmap (span, nSpans, hspan, hSpans, bitmap, bitmap_state, from->next, opts->sFlag);
-               bUsedYYBitmap = true;
+               info.bitmap = new GoBitmap (span, nSpans, hspan, hSpans, bm, bms, from->next, opts->sFlag);
+               bitmaps.used = true;
        }
        else
        {
index d1bfc51d7e27ec9feea8175959f2c01eb73cc5cd..4d158ea72f364a50651e31d9a5efe0b17cee3167 100644 (file)
@@ -4,7 +4,6 @@
 namespace re2c
 {
 
-extern bool bUsedYYBitmap;
 extern bool bWroteGetState;
 extern bool bWroteCondCheck;
 
index af7d487887630ebf90006068de2170bd1395f5c9..0056fdc5f77096fbce63d02f5aade6d36e9478c1 100644 (file)
@@ -45,6 +45,7 @@ DFA::DFA
        , maxtagver (dfa.maxtagver)
        , def_rule (def)
        , key_size (key)
+       , bitmaps (std::min(ubChar, 256u))
 {
        const size_t nstates = dfa.states.size();
        const size_t nchars = dfa.nchars;
index 1bc1f3d81ac39512a3d149bd8891a76c957a6897..d5936bd5799701a6c7aa727ab752d173f6f52041 100644 (file)
@@ -7,6 +7,7 @@
 #include <string>
 #include <valarray>
 
+#include "src/codegen/bitmap.h"
 #include "src/codegen/go.h"
 #include "src/codegen/label.h"
 #include "src/ir/adfa/action.h"
@@ -78,6 +79,7 @@ struct DFA
        tagver_t maxtagver;
        const size_t def_rule;
        const size_t key_size;
+       bitmaps_t bitmaps;
 
        DFA     ( const dfa_t &dfa
                , const std::vector<size_t> &fill
index 0de6dd97fce9c5a08cde4d200e57818571ad1d06..346e78c4d9be924cb4590309e5a0301cfcb00cbe 100644 (file)
@@ -102,8 +102,6 @@ void DFA::findBaseState()
 
 void DFA::prepare (Opt &opts)
 {
-       bUsedYYBitmap = false;
-
        // create rule states
        std::vector<State*> rule2state(rules.size());
        for (State *s = head; s; s = s->next) {
@@ -170,9 +168,8 @@ void DFA::prepare (Opt &opts)
                                        s->isBase = true;
                                        split(s);
 
-                                       if (opts->bFlag)
-                                       {
-                                               BitMap::find(&s->next->go, s);
+                                       if (opts->bFlag) {
+                                               bitmaps.insert(&s->next->go, s);
                                        }
 
                                        s = s->next;
@@ -184,9 +181,8 @@ void DFA::prepare (Opt &opts)
        // find ``base'' state, if possible
        findBaseState();
 
-       for (State * s = head; s; s = s->next)
-       {
-               s->go.init (s, opts);
+       for (State *s = head; s; s = s->next) {
+               s->go.init(s, opts, bitmaps);
        }
 }
 
index 406b45359e7efdde8161fb094b6a00032d9d540f..d306c2c629e7f7080d3f2de62f8891715b8c35ba 100644 (file)
@@ -94,7 +94,8 @@ void emit_prolog(OutputFile &o)
 
 void emit_start(OutputFile &o, size_t maxfill, const std::string &name,
        size_t sizeof_key, size_t def, bool backup, bool accept, bool oldstyle_ctxmarker,
-       const std::set<std::string> &tagnames, const std::set<std::string> &tagvars)
+       const std::set<std::string> &tagnames, const std::set<std::string> &tagvars,
+       bitmaps_t &bitmaps)
 {
        Opt &opts = o.opts;
        const size_t sizeof_cunit = opts->encoding.szCodeUnit();
@@ -284,8 +285,8 @@ void emit_start(OutputFile &o, size_t maxfill, const std::string &name,
        }
 
        o.ws("\n");
-       if (opts->bFlag && BitMap::first) {
-               BitMap::gen(o, 2, 0, std::min(0x100u, opts->encoding.nCodeUnits()));
+       if (opts->bFlag) {
+               bitmaps.gen(o, 2);
        }
        o.ws("\n");
 }
index ce1c9919949643edb939c88434b36f45d698feb6..e9ed4985a25860ebf7d9b89b34738568ebec25e6 100644 (file)
@@ -11,6 +11,7 @@
 #include <vector>
 #include <utility>
 
+#include "src/codegen/bitmap.h"
 #include "src/ir/regexp/regexp.h"
 #include "src/ir/rule.h"
 #include "src/ir/tcmd.h"
@@ -102,7 +103,8 @@ void emit_data(const Skeleton &skel, std::string fname, size_t cunit_size);
 void emit_prolog(OutputFile & o);
 void emit_start(OutputFile &o, size_t maxfill, const std::string &name,
        size_t sizeof_key, size_t def, bool backup, bool accept, bool oldstyle_ctxmarker,
-       const std::set<std::string> &tagnames, const std::set<std::string> &tagvars);
+       const std::set<std::string> &tagnames, const std::set<std::string> &tagvars,
+       bitmaps_t &bitmaps);
 void emit_end(OutputFile &o, const std::string &name, bool backup, bool oldstyle_ctxmarker);
 void emit_epilog(OutputFile &o, const std::set<std::string> &names);
 void emit_action(OutputFile &o, uint32_t ind, const DFA &dfa, size_t rid);
index 6760a4e3217773065a6a9606db025de685614031..f5029811e5a34e2fda2a63ee24ccda76b04b442c 100644 (file)
@@ -13,7 +13,6 @@
 namespace re2c
 {
 
-bool bUsedYYBitmap  = false;
 bool bWroteGetState = false;
 bool bWroteCondCheck = false;