Go to the documentation of this file.
13 #include <unordered_map>
16 #include "util/logging.h"
21 #include "re2/regexp.h"
22 #include "re2/walker-inl.h"
69 return {l1.head, l2.tail};
95 class Compiler :
public Regexp::Walker<Frag> {
119 Frag
PostVisit(Regexp* re, Frag parent_arg, Frag pre_arg, Frag* child_args,
125 Frag
Plus(Frag a,
bool nongreedy);
126 Frag
Star(Frag a,
bool nongreedy);
127 Frag
Quest(Frag a,
bool nongreedy);
133 Frag
Cat(Frag a, Frag
b);
134 Frag
Alt(Frag a, Frag
b);
146 Frag
ByteRange(
int lo,
int hi,
bool foldcase);
208 PODArray<Prog::Inst>
inst_;
247 int cap =
inst_.size();
252 PODArray<Prog::Inst> inst(cap);
253 if (
inst_.data() != NULL)
285 a.end.head == (
a.begin << 1) &&
295 return Frag(
b.begin,
a.end,
b.nullable &&
a.nullable);
299 return Frag(
a.begin,
b.end,
a.nullable &&
b.nullable);
316 a.nullable ||
b.nullable);
340 return Frag(
a.begin, pl,
a.nullable);
349 return Quest(
Plus(a, nongreedy), nongreedy);
363 return Frag(
id, pl,
true);
389 inst_[
id].InitByteRange(lo, hi, foldcase, 0);
427 inst_[
id].InitCapture(2*n,
a.begin);
428 inst_[
id+1].InitCapture(2*n+1, 0);
481 std::unordered_map<uint64_t, int>::const_iterator
it =
rune_cache_.find(
key);
492 bool foldcase =
inst_[
id].foldcase() != 0;
539 else if (
f.end.head&1)
540 br =
inst_[
f.begin].out1();
542 br =
inst_[
f.begin].out();
557 else if (
f.end.head&1)
558 inst_[
f.begin].out1_ = br;
560 inst_[
f.begin].set_out(br);
584 inst_[id1].foldcase() ==
inst_[id2].foldcase();
615 LOG(DFATAL) <<
"should never happen";
643 if (lo > hi || lo > 0xFF)
648 static_cast<uint8_t>(hi), foldcase, 0));
696 if (lo == 0x80 && hi == 0x10ffff) {
704 if (lo <=
max &&
max < hi) {
714 static_cast<uint8_t>(hi), foldcase, 0));
721 if ((lo & ~
m) != (hi & ~
m)) {
737 int n =
runetochar(
reinterpret_cast<char*
>(ulo), &lo);
738 int m =
runetochar(
reinterpret_cast<char*
>(uhi), &hi);
768 for (
int i = 0;
i <
n;
i++) {
771 if (i == 0 || (ulo[i] == uhi[i] && i != n-1))
777 for (
int i = n-1;
i >= 0;
i--) {
780 if (i == n-1 || (ulo[i] < uhi[i] && i != 0))
792 LOG(DFATAL) <<
"Compiler::Copy called!";
827 for (
int i = 1;
i <
n;
i++)
856 Frag
f =
Match(re->match_id());
866 Frag
f = child_frags[0];
867 for (
int i = 1;
i < nchild_frags;
i++)
868 f =
Cat(f, child_frags[i]);
873 Frag
f = child_frags[0];
874 for (
int i = 1;
i < nchild_frags;
i++)
875 f =
Alt(f, child_frags[i]);
893 if (re->nrunes() == 0)
896 for (
int i = 0;
i < re->nrunes();
i++) {
916 CharClass* cc = re->cc();
919 LOG(DFATAL) <<
"No ranges in char class";
930 bool foldascii = cc->FoldsASCII();
937 if (foldascii &&
'A' <=
i->lo &&
i->hi <=
'Z')
942 bool fold = foldascii;
943 if ((
i->lo <=
'A' &&
'z' <=
i->hi) ||
i->hi <
'A' ||
'z' <
i->lo ||
944 (
'Z' <
i->lo &&
i->hi <
'a'))
956 return child_frags[0];
957 return Capture(child_frags[0], re->cap());
977 LOG(DFATAL) <<
"Missing case in Compiler: " << re->op();
992 if (re == NULL ||
depth >= 4)
998 if (re->
nsub() > 0) {
1003 for (
int i = 1;
i < re->
nsub();
i++)
1039 if (re == NULL ||
depth >= 4)
1045 if (re->
nsub() > 0) {
1049 subcopy[re->
nsub() - 1] = sub;
1050 for (
int i = 0;
i < re->
nsub() - 1;
i++)
1083 }
else if (
static_cast<size_t>(max_mem) <=
sizeof(Prog)) {
1087 int64_t m = (max_mem -
sizeof(Prog)) /
sizeof(Prog::Inst);
1118 Regexp* sre = re->Simplify();
1128 Frag
all =
c.WalkExponential(sre, Frag(), 2*
c.max_ninst_);
1136 c.reversed_ =
false;
1140 if (
c.prog_->reversed()) {
1141 c.prog_->set_anchor_start(is_anchor_end);
1142 c.prog_->set_anchor_end(is_anchor_start);
1144 c.prog_->set_anchor_start(is_anchor_start);
1145 c.prog_->set_anchor_end(is_anchor_end);
1148 c.prog_->set_start(
all.begin);
1149 if (!
c.prog_->anchor_start()) {
1153 c.prog_->set_start_unanchored(
all.begin);
1156 return c.Finish(re);
1178 bool prefix_foldcase;
1217 c.Setup(re->parse_flags(), max_mem, anchor);
1219 Regexp* sre = re->Simplify();
1223 Frag
all =
c.WalkExponential(sre, Frag(), 2*
c.max_ninst_);
1228 c.prog_->set_anchor_start(
true);
1229 c.prog_->set_anchor_end(
true);
1236 c.prog_->set_start(
all.begin);
1237 c.prog_->set_start_unanchored(
all.begin);
1239 Prog*
prog =
c.Finish(re);
1245 bool dfa_failed =
false;
1246 StringPiece sp =
"hello, world";
1248 NULL, &dfa_failed, NULL);
static void Patch(Prog::Inst *inst0, PatchList l, uint32_t p)
static PatchList Append(Prog::Inst *inst0, PatchList l1, PatchList l2)
std::unordered_map< uint64_t, int > rune_cache_
static PatchList Append(Prog::Inst *inst0, PatchList l1, PatchList l2)
return memset(p, 0, total)
Frag ShortVisit(Regexp *re, Frag parent_arg)
Frag Plus(Frag a, bool nongreedy)
static Regexp * Capture(Regexp *sub, ParseFlags flags, int cap)
static void Patch(Prog::Inst *inst0, PatchList l, uint32_t v)
static Regexp * Concat(Regexp **subs, int nsubs, ParseFlags flags)
Prog * CompileToProg(int64_t max_mem)
static const PatchList kNullPatchList
void Setup(Regexp::ParseFlags, int64_t, RE2::Anchor)
Frag PostVisit(Regexp *re, Frag parent_arg, Frag pre_arg, Frag *child_args, int nchild_args)
static Regexp * LiteralString(Rune *runes, int nrunes, ParseFlags flags)
static bool IsNoMatch(Frag a)
void AddRuneRange(Rune lo, Rune hi, bool foldcase)
static bool IsAnchorStart(Regexp **pre, int depth)
Frag(uint32_t begin, PatchList end, bool nullable)
constexpr absl::remove_reference_t< T > && move(T &&t) noexcept
Frag ByteRange(int lo, int hi, bool foldcase)
RefCountedPtr< grpc_tls_certificate_provider > root
static uint64_t MakeRuneCacheKey(uint8_t lo, uint8_t hi, bool foldcase, int next)
bool RequiredPrefixForAccel(std::string *prefix, bool *foldcase)
int runetochar(char *str, const Rune *rune)
Poll< absl::StatusOr< std::tuple< T... > > > fail()
unsigned __int64 uint64_t
Frag Literal(Rune r, bool foldcase)
void set_dfa_mem(int64_t dfa_mem)
static const int kMaxInst
Frag Star(Frag a, bool nongreedy)
static bool IsAnchorEnd(Regexp **pre, int depth)
int UncachedRuneByteSuffix(uint8_t lo, uint8_t hi, bool foldcase, int next)
bool IsCachedRuneByteSuffix(int id)
static Prog * Compile(Regexp *re, bool reversed, int64_t max_mem)
Frag EmptyWidth(EmptyOp op)
Prog * CompileToReverseProg(int64_t max_mem)
void ConfigurePrefixAccel(const std::string &prefix, bool prefix_foldcase)
PODArray< Prog::Inst > inst_
bool ByteRangeEqual(int id1, int id2)
#define DCHECK_EQ(val1, val2)
void AddRuneRangeLatin1(Rune lo, Rune hi, bool foldcase)
static PatchList Mk(uint32_t p)
AllocList * next[kMaxLevel]
static Prog * CompileSet(Regexp *re, RE2::Anchor anchor, int64_t max_mem)
static const char prefix[]
int AddSuffixRecursive(int root, int id)
Frag Quest(Frag a, bool nongreedy)
void AddRuneRangeUTF8(Rune lo, Rune hi, bool foldcase)
static int MaxRune(int len)
static PatchList Mk(uint32_t p)
#define DCHECK(condition)
Compiler & operator=(const Compiler &)=delete
Frag PreVisit(Regexp *re, Frag parent_arg, bool *stop)
int CachedRuneByteSuffix(uint8_t lo, uint8_t hi, bool foldcase, int next)
Frag Capture(Frag a, int n)
Frag FindByteRange(int root, int id)
static Prog * CompileSet(Regexp *re, RE2::Anchor anchor, int64_t max_mem)
grpc
Author(s):
autogenerated on Fri May 16 2025 02:58:00