MySQL 9.3.0
Source Code Documentation
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages Concepts
rpn.h
Go to the documentation of this file.
1/*
2 * Copyright (c) 2024, 2025, Oracle and/or its affiliates.
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License, version 2.0,
6 * as published by the Free Software Foundation.
7 *
8 * This program is designed to work with certain software (including
9 * but not limited to OpenSSL) that is licensed under separate terms,
10 * as designated in a particular file or component or in included license
11 * documentation. The authors of MySQL hereby grant you an additional
12 * permission to link the program and your derivative works with the
13 * separately licensed software that they have either included with
14 * the program or referenced in the documentation.
15 *
16 * This program is distributed in the hope that it will be useful, but
17 * WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
19 * the GNU General Public License, version 2.0, for more details.
20 *
21 * You should have received a copy of the GNU General Public License
22 * along with this program; if not, write to the Free Software Foundation, Inc.,
23 * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
24 */
25
26#ifndef ROUTER_SRC_ROUTING_GUIDELINES_SRC_RPN_H_
27#define ROUTER_SRC_ROUTING_GUIDELINES_SRC_RPN_H_
28
29#include <cmath>
30#include <concepts>
31#include <exception>
32#include <functional>
33#include <memory>
34#include <string>
35#include <type_traits>
36#include <unordered_map>
37#include <utility>
38#include <variant>
39#include <vector>
40
43
44namespace routing_guidelines {
45class Rules_parser;
46class Routing_guidelines_parser_test;
47class Routing_guidelines_document_parser;
48
49namespace rpn {
50
51struct Function_definition;
52
53class Token final {
54 public:
55 enum class Type {
56 NUM,
57 STR,
58 BOOL,
59 ROLE,
60 LIST,
61 NONE,
62 ADD,
63 MIN,
64 DIV,
65 MUL,
66 MOD,
67 NEG,
68 LT,
69 GT,
70 NE,
71 LE,
72 GE,
73 EQ,
74 IN_OP,
75 NOT,
76 AND,
77 MID_AND,
78 OR,
79 MID_OR,
80 TAG_REF,
81 VAR_REF,
82 FUNC,
85 CONCAT,
86 REGEXP,
88 };
89
90 struct Location {
91 int start;
92 int end;
93 };
94
95 struct Function {
98 };
99
100 Token() : type_(Type::NONE), value_(0.0) {}
101
102 Token(Type type, int start, int end)
103 : type_(type), value_(Location{start, end}) {}
104
105 template <typename T>
106 requires std::is_arithmetic_v<T>
107 explicit Token(T v, Type type = Type::NUM)
108 : type_(type), value_(static_cast<double>(v)) {}
109
110 template <typename T>
111 requires std::is_constructible_v<std::string, T>
112 explicit Token(T &&s, Type type = Type::STR)
113 : type_(type), value_(std::string(std::forward<T>(s))) {}
114
115 explicit Token(bool val) : type_(Type::BOOL), value_(val ? 1.0 : 0.0) {}
116
117 Token(const Function_definition &function, int start, int end)
118 : type_(Type::FUNC), value_(Function{&function, {start, end}}) {}
119
120 Token(const Token &i) = default;
121 Token(Token &&i) noexcept = default;
122
123 static Token regexp(const std::string &rgx);
124
125 Token &operator=(const Token &i) = default;
126 Token &operator=(Token &&i) noexcept = default;
127
128 bool is_num() const { return type_ == Type::NUM; }
129
130 bool is_role() const { return type_ == Type::ROLE; }
131
132 double get_num() const { return std::get<double>(value_); }
133
134 bool is_bool() const { return type_ == Type::BOOL; }
135
136 bool get_bool(const char *exception_msg = nullptr) const;
137
138 bool is_string() const { return type_ == Type::STR; }
139
140 const std::string &get_string() const {
141 if (std::holds_alternative<std::string>(value_)) {
142 return std::get<std::string>(value_);
143 }
144 throw std::runtime_error("Type error, expected string");
145 }
146
147 bool is_null() const { return type_ == Type::NONE; }
148
149 double &number() { return std::get<double>(value_); }
150
151 const double &number() const { return std::get<double>(value_); }
152
153 const std::string &string() const { return std::get<std::string>(value_); }
154
155 std::string &string() { return std::get<std::string>(value_); }
156
157 bool has_location() const {
158 return std::holds_alternative<Location>(value_) ||
159 std::holds_alternative<Function>(value_);
160 }
161
162 const Location &location() const {
163 return std::holds_alternative<Function>(value_)
164 ? std::get<Function>(value_).location
165 : std::get<Location>(value_);
166 }
167
168 const Function_definition &function() const {
169 return *std::get<Function>(value_).definition;
170 }
171
172 Type type() const { return type_; }
173
174 template <class Visitor>
175 constexpr auto visit(Visitor &&vis) const {
176 return std::visit(vis, value_);
177 }
178
179 private:
181
182 std::variant<double, std::string, Location, Function> value_;
183
184 friend bool operator==(const Token &lhs, const Token &rhs);
185 friend bool operator<(const Token &lhs, const Token &rhs);
186 friend bool operator<=(const Token &lhs, const Token &rhs);
187};
188
189inline bool operator!=(const Token &lhs, const Token &rhs) {
190 return !(lhs == rhs);
191}
192inline bool operator>(const Token &lhs, const Token &rhs) { return rhs < lhs; }
193inline bool operator>=(const Token &lhs, const Token &rhs) {
194 return rhs <= lhs;
195}
196
197std::string to_string(const Token::Type tt);
198std::string to_string(const Token &token, bool print_value = false);
199
201 const char *name;
202 std::vector<rpn::Token::Type> args;
204 void (*reducer)(std::vector<Token> *);
205
206 void reduce(std::vector<rpn::Token> *stack) const;
207};
208
209class Context final {
210 public:
211 Context();
212 Context(const Context &) = delete;
213 Context &operator=(const Context &) = delete;
214
215 Token get_tag(std::string_view name) const;
216 Token get(const std::string &name) const;
217 Token get(int offset) const { return context_vars_[offset](); }
218 Token::Type get_type(std::string_view name, int *offset) const;
219 std::optional<std::string> get_var_name(const Token &tok) const;
220
221 template <class T>
222 void set(const std::string &name, T &&value) {
223 context_vars_.emplace_back(
224 [t = Token(std::forward<T>(value))]() { return t; });
225 context_[name] = context_vars_.size() - 1;
226 }
227
229 server_ = &server_info;
230 }
231
232 void clear_server_info() { server_ = nullptr; }
233
235 session_ = &session_info;
236 }
237
238 void clear_session_info() { session_ = nullptr; }
239
241 sql_ = &sql_info;
242 }
243
244 void clear_sql_info() { sql_ = nullptr; }
245
247 router_ = &router_info;
248 }
249
250 void clear_router_info() { router_ = nullptr; }
251
252 bool parse_tags_toggled();
253
255
257 version_ = std::move(version);
258 }
259
260 private:
261 std::unique_ptr<bool, std::function<void(bool *)>> start_parse_mode() {
262 parse_mode_ = true;
263 return std::unique_ptr<bool, std::function<void(bool *)>>(
264 &parse_mode_, [](bool *b) { *b = false; });
265 }
266
267 Token handle_miss(std::string_view name) const;
268
269 const routing_guidelines::Router_info *router_{nullptr};
270 const routing_guidelines::Server_info *server_ = nullptr;
271 const routing_guidelines::Session_info *session_ = nullptr;
272 const routing_guidelines::Sql_info *sql_ = nullptr;
273
274 std::map<std::string, int, std::less<>> context_;
275 std::vector<std::function<Token()>> context_vars_;
276 bool parse_mode_{false};
277 bool extended_session_info_{false};
278 bool parsing_tags_{false};
281
283};
284
286 public:
287 Expression() = default;
288 Expression(const std::vector<Token> &rpn, std::string code)
289 : rpn_(rpn), code_(std::move(code)) {}
290 Expression(std::vector<Token> &&rpn, std::string code)
291 : rpn_(std::move(rpn)), code_(std::move(code)) {}
292
293 Token eval(Context *variables,
294 const Routing_guidelines_engine::ResolveCache *cache = nullptr,
295 const bool dry_run = false) const;
296
297 bool verify(Context *variables) const;
298
299 std::string variable() const { return rpn_.back().string(); }
300
301 bool empty() { return rpn_.empty(); }
302 void clear();
303
304 friend bool operator==(const Expression &lhs, const Expression &rhs);
305 friend bool operator!=(const Expression &lhs, const Expression &rhs);
306
307 private:
308 std::vector<Token> rpn_;
309 std::string code_;
310
313};
314
315std::string error_msg(const char *msg, const std::string &exp, int beg,
316 int end);
317
318std::vector<std::string_view> get_variables_names();
319
320} // namespace rpn
321} // namespace routing_guidelines
322
323#endif // ROUTER_SRC_ROUTING_GUIDELINES_SRC_RPN_H_
std::unordered_map< std::string, net::ip::address > ResolveCache
Map with preprocessed resolved hostnames.
Definition: routing_guidelines.h:188
Conducting the whole scanning and parsing of routing guidelines rules.
Definition: rules_parser.h:74
mysqlrouter::RoutingGuidelinesVersion get_version() const
Definition: rpn.h:254
void clear_sql_info()
Definition: rpn.h:244
std::unique_ptr< bool, std::function< void(bool *)> > start_parse_mode()
Definition: rpn.h:261
Context & operator=(const Context &)=delete
void clear_server_info()
Definition: rpn.h:232
void set_server_info(const routing_guidelines::Server_info &server_info)
Definition: rpn.h:228
void set_sql_info(const routing_guidelines::Sql_info &sql_info)
Definition: rpn.h:240
Context(const Context &)=delete
void set(const std::string &name, T &&value)
Definition: rpn.h:222
void set_router_info(const routing_guidelines::Router_info &router_info)
Definition: rpn.h:246
Token get(int offset) const
Definition: rpn.h:217
std::vector< std::function< Token()> > context_vars_
Definition: rpn.h:275
void clear_router_info()
Definition: rpn.h:250
std::map< std::string, int, std::less<> > context_
Definition: rpn.h:274
void set_version(mysqlrouter::RoutingGuidelinesVersion version)
Definition: rpn.h:256
void set_session_info(const routing_guidelines::Session_info &session_info)
Definition: rpn.h:234
void clear_session_info()
Definition: rpn.h:238
Expression(const std::vector< Token > &rpn, std::string code)
Definition: rpn.h:288
friend Routing_guidelines_document_parser
Definition: rpn.h:312
std::string code_
Definition: rpn.h:309
Expression(std::vector< Token > &&rpn, std::string code)
Definition: rpn.h:290
bool empty()
Definition: rpn.h:301
friend Routing_guidelines_parser_test
Definition: rpn.h:311
std::string variable() const
Definition: rpn.h:299
std::vector< Token > rpn_
Definition: rpn.h:308
Definition: rpn.h:53
Token(Token &&i) noexcept=default
bool has_location() const
Definition: rpn.h:157
Token(const Token &i)=default
bool is_string() const
Definition: rpn.h:138
const Function_definition & function() const
Definition: rpn.h:168
std::variant< double, std::string, Location, Function > value_
Definition: rpn.h:182
bool is_num() const
Definition: rpn.h:128
std::string & string()
Definition: rpn.h:155
bool is_role() const
Definition: rpn.h:130
double & number()
Definition: rpn.h:149
Type type_
Definition: rpn.h:180
Type
Definition: rpn.h:55
Token(T &&s, Type type=Type::STR)
Definition: rpn.h:112
bool is_null() const
Definition: rpn.h:147
const double & number() const
Definition: rpn.h:151
Token(const Function_definition &function, int start, int end)
Definition: rpn.h:117
Token()
Definition: rpn.h:100
Token(Type type, int start, int end)
Definition: rpn.h:102
bool is_bool() const
Definition: rpn.h:134
Token & operator=(const Token &i)=default
Token(T v, Type type=Type::NUM)
Definition: rpn.h:107
Type type() const
Definition: rpn.h:172
Token & operator=(Token &&i) noexcept=default
const Location & location() const
Definition: rpn.h:162
double get_num() const
Definition: rpn.h:132
Token(bool val)
Definition: rpn.h:115
const std::string & get_string() const
Definition: rpn.h:140
constexpr auto visit(Visitor &&vis) const
Definition: rpn.h:175
const std::string & string() const
Definition: rpn.h:153
static Gcs_tagged_lock::Tag get_tag(std::uint64_t const &lock_word)
Definition: gcs_tagged_lock.cc:36
mrs::interface::RestHandler::HttpResult::Type Type
Definition: handler_content_file.cc:42
static void start(mysql_harness::PluginFuncEnv *env)
Definition: http_auth_backend_plugin.cc:180
#define T
Definition: jit_executor_value.cc:373
static std::string to_string(const LEX_STRING &str)
Definition: lex_string.h:50
bool operator==(const my_thread_handle &a, const my_thread_handle &b)
Definition: my_thread.h:151
static void print_value(FILE *file, MYSQL_RES *result, MYSQL_ROW row, const char *prefix, const char *name, int string_value)
Definition: mysqldump.cc:5765
ValueType value(const std::optional< ValueType > &v)
Definition: gtid.h:83
@ NONE
Definition: base.h:45
static mysql_service_status_t get(THD **thd) noexcept
Definition: mysql_current_thread_reader_all_empty.cc:31
constexpr RoutingGuidelinesVersion kBaseRoutingGuidelines
Definition: routing_guidelines_version.h:39
bool verify(const std::string &digest, const std::string &message, const std::string &public_key_content)
Verify a message signed by the private key pair of the provided public key.
Definition: my_base64_encode.cc:113
static mysql_service_status_t clear(reference_caching_channel channel) noexcept
Definition: component.cc:146
Definition: errors.cc:45
std::vector< std::string_view > get_variables_names()
Definition: rpn.cc:851
bool operator<(const Token &lhs, const Token &rhs)
Definition: rpn.cc:126
bool operator>(const Token &lhs, const Token &rhs)
Definition: rpn.h:192
bool operator<=(const Token &lhs, const Token &rhs)
Definition: rpn.cc:140
bool operator==(const Token &lhs, const Token &rhs)
Definition: rpn.cc:107
std::string error_msg(const char *msg, const std::string &exp, int beg, int end)
Definition: rpn.cc:838
bool operator>=(const Token &lhs, const Token &rhs)
Definition: rpn.h:193
bool operator!=(const Token &lhs, const Token &rhs)
Definition: rpn.h:189
Definition: routing_guidelines_datatypes.h:31
Definition: gcs_xcom_synode.h:64
std::vector< T, ut::allocator< T > > vector
Specialization of vector which uses allocator.
Definition: ut0new.h:2876
std::conditional_t< !std::is_array< T >::value, std::unique_ptr< T, detail::Deleter< T > >, std::conditional_t< detail::is_unbounded_array_v< T >, std::unique_ptr< T, detail::Array_deleter< std::remove_extent_t< T > > >, void > > unique_ptr
The following is a common type that is returned by all the ut::make_unique (non-aligned) specializati...
Definition: ut0new.h:2440
required uint64 version
Definition: replication_group_member_actions.proto:41
@ NUM
Definition: sql_yacc.h:425
case opt name
Definition: sslopt-case.h:29
Definition: routing_guidelines_version.h:37
Information about this Router instance.
Definition: routing_guidelines.h:59
Information about one server destination.
Definition: routing_guidelines.h:80
Information about incoming session.
Definition: routing_guidelines.h:103
Information about query details.
Definition: routing_guidelines.h:117
rpn::Token::Type ret_val
Definition: rpn.h:203
std::vector< rpn::Token::Type > args
Definition: rpn.h:202
const char * name
Definition: rpn.h:201
Location location
Definition: rpn.h:97
const Function_definition * definition
Definition: rpn.h:96
task_env * stack
Definition: task.cc:896
const char * get_type(TYPELIB *typelib, unsigned int nr)