1/*
2 * Copyright (c) 2015-2017, Intel Corporation
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are met:
6 *
7 * * Redistributions of source code must retain the above copyright notice,
8 * this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of Intel Corporation nor the names of its contributors
13 * may be used to endorse or promote products derived from this software
14 * without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
20 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26 * POSSIBILITY OF SUCH DAMAGE.
27 */
28
29/** \file
30 * \brief Rose Build interface.
31 *
32 * Rose Build interface. Everything you ever needed to feed literals in and
33 * get a RoseEngine out. This header should be everything needed by the rest
34 * of UE2.
35 */
36
37#ifndef ROSE_BUILD_H
38#define ROSE_BUILD_H
39
40#include "ue2common.h"
41#include "rose_common.h"
42#include "rose_in_graph.h"
43#include "util/bytecode_ptr.h"
44#include "util/charreach.h"
45#include "util/flat_containers.h"
46#include "util/noncopyable.h"
47#include "util/ue2string.h"
48
49#include <memory>
50#include <set>
51#include <utility>
52#include <vector>
53
54struct NFA;
55struct SmallWriteEngine;
56struct RoseEngine;
57
58namespace ue2 {
59
60struct BoundaryReports;
61struct CompileContext;
62struct raw_puff;
63struct raw_som_dfa;
64class CharReach;
65class NGHolder;
66class ReportManager;
67class SmallWriteBuild;
68class SomSlotManager;
69
70class RoseDedupeAux {
71public:
72 virtual ~RoseDedupeAux();
73
74 /** \brief True if we can not establish that at most a single callback will
75 * be generated at a given offset from this set of reports. */
76 virtual bool requiresDedupeSupport(const flat_set<ReportID> &reports)
77 const = 0;
78};
79
80/** \brief Abstract interface intended for callers from elsewhere in the tree,
81 * real underlying implementation is RoseBuildImpl in rose_build_impl.h. */
82class RoseBuild : noncopyable {
83public:
84 virtual ~RoseBuild();
85
86 /** \brief Adds a single literal. */
87 virtual void add(bool anchored, bool eod, const ue2_literal &lit,
88 const flat_set<ReportID> &ids) = 0;
89
90 virtual bool addRose(const RoseInGraph &ig, bool prefilter) = 0;
91 virtual bool addSombeRose(const RoseInGraph &ig) = 0;
92
93 virtual bool addOutfix(const NGHolder &h) = 0;
94 virtual bool addOutfix(const NGHolder &h, const raw_som_dfa &haig) = 0;
95 virtual bool addOutfix(const raw_puff &rp) = 0;
96
97 virtual bool addChainTail(const raw_puff &rp, u32 *queue_out,
98 u32 *event_out) = 0;
99
100 /** \brief Returns true if we were able to add it as a mask. */
101 virtual bool add(bool anchored, const std::vector<CharReach> &mask,
102 const flat_set<ReportID> &reports) = 0;
103
104 /** \brief Attempts to add the graph to the anchored acyclic table. Returns
105 * true on success. */
106 virtual bool addAnchoredAcyclic(const NGHolder &graph) = 0;
107
108 virtual bool validateMask(const std::vector<CharReach> &mask,
109 const flat_set<ReportID> &reports,
110 bool anchored, bool eod) const = 0;
111 virtual void addMask(const std::vector<CharReach> &mask,
112 const flat_set<ReportID> &reports, bool anchored,
113 bool eod) = 0;
114
115 /** \brief Construct a runtime implementation. */
116 virtual bytecode_ptr<RoseEngine> buildRose(u32 minWidth) = 0;
117
118 virtual std::unique_ptr<RoseDedupeAux> generateDedupeAux() const = 0;
119
120 /** Get a unique report identifier for a prefix|infix engine */
121 virtual ReportID getNewNfaReport() = 0;
122
123 /** Note that we have seen a SOM pattern. */
124 virtual void setSom() = 0;
125};
126
127// Construct a usable Rose builder.
128std::unique_ptr<RoseBuild> makeRoseBuilder(ReportManager &rm,
129 SomSlotManager &ssm,
130 SmallWriteBuild &smwr,
131 const CompileContext &cc,
132 const BoundaryReports &boundary);
133
134bool roseCheckRose(const RoseInGraph &ig, bool prefilter,
135 const ReportManager &rm, const CompileContext &cc);
136
137bool roseIsPureLiteral(const RoseEngine *t);
138
139size_t maxOverlap(const ue2_literal &a, const ue2_literal &b, u32 b_delay);
140
141} // namespace ue2
142
143#endif // ROSE_BUILD_H
144