1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright (C) 2020 Marvell International Ltd.
3  */
4 
5 #include <rte_malloc.h>
6 #include <rte_regexdev.h>
7 
8 #include "otx2_regexdev.h"
9 #include "otx2_regexdev_compiler.h"
10 #include "otx2_regexdev_mbox.h"
11 
12 #ifdef REE_COMPILER_SDK
13 #include <rxp-compiler.h>
14 
15 static int
ree_rule_db_compile(const struct rte_regexdev_rule * rules,uint16_t nb_rules,struct rxp_rof ** rof,struct rxp_rof ** rofi,struct rxp_rof * rof_for_incremental_compile,struct rxp_rof * rofi_for_incremental_compile)16 ree_rule_db_compile(const struct rte_regexdev_rule *rules,
17 		uint16_t nb_rules, struct rxp_rof **rof, struct rxp_rof **rofi,
18 		struct rxp_rof *rof_for_incremental_compile,
19 		struct rxp_rof *rofi_for_incremental_compile)
20 {
21 	/*INPUT*/
22 	struct rxp_prefix_selection_control_list *prefix_selection_control_list
23 		= NULL;
24 	struct rxp_blacklist_data_sample *blacklist_sample_data = NULL;
25 	struct rxp_rule_ids_to_remove *rule_ids_to_remove = NULL;
26 	struct rxp_roff *roff_for_incremental_compile = NULL;
27 
28 	/*OPTIONS - setting default values*/
29 	enum rxp_virtual_prefix_mode virtual_prefix_mode =
30 			RXP_VIRTUAL_PREFIX_MODE_0;
31 	enum rxp_prefix_capacity prefix_capacity = RXP_PREFIX_CAPACITY_32K;
32 	/**< rxp_global_regex_options_flags*/
33 	enum rxp_compiler_objective objective = RXP_COMPILER_OBJECTIVE_5;
34 	enum rxp_tpe_data_width tpe_data_width = RXP_TPE_DATA_WIDTH_4;
35 	uint32_t compiler_options = RXP_COMPILER_OPTIONS_FORCE;
36 	/**< rxp_compiler_options_flags*/
37 	enum rxp_verbose_level verbose = RXP_VERBOSE_LEVEL_3;
38 	enum rxp_version set_rxp_version = RXP_VERSION_V5_8;
39 	uint32_t compiler_output_flags = 0;
40 	/**< rxp_compiler_output_flags*/
41 	uint32_t global_regex_options = 0;
42 	/**< rxp_global_regex_options_flags*/
43 	float set_auto_blacklist = 0;
44 	uint32_t max_rep_max = 65535;
45 	uint32_t divide_ruleset = 1;
46 	struct rxp_ruleset ruleset;
47 	float ptpb_threshold = 0;
48 	uint32_t set_max = 0;
49 	uint32_t threads = 1;
50 
51 	/*OUTPUT*/
52 	struct rxp_rule_direction_analysis *rule_direction_analysis = NULL;
53 	struct rxp_compilation_statistics *compilation_statistics = NULL;
54 	struct rxp_prefix_selection_control_list *generated_pscl = NULL;
55 	struct rxp_uncompiled_rules_log *uncompiled_rules_log = NULL;
56 	struct rxp_critical_rules_rank *critical_rules_rank = NULL;
57 	struct rxp_compiled_rules_log *compiled_rules_log = NULL;
58 	struct rxp_roff *roff = NULL;
59 
60 	uint16_t i;
61 	int ret;
62 
63 	ruleset.number_of_entries = nb_rules;
64 	ruleset.rules = rte_malloc("rxp_rule_entry",
65 			nb_rules*sizeof(struct rxp_rule_entry), 0);
66 
67 	if (ruleset.rules == NULL) {
68 		otx2_err("Could not allocate memory for rule compilation\n");
69 		return -EFAULT;
70 	}
71 	if (rof_for_incremental_compile)
72 		compiler_options |= RXP_COMPILER_OPTIONS_INCREMENTAL;
73 	if (rofi_for_incremental_compile)
74 		compiler_options |= RXP_COMPILER_OPTIONS_CHECKSUM;
75 
76 	for (i = 0; i < nb_rules; i++) {
77 		ruleset.rules[i].number_of_prefix_entries = 0;
78 		ruleset.rules[i].prefix = NULL;
79 		ruleset.rules[i].rule = rules[i].pcre_rule;
80 		ruleset.rules[i].rule_id = rules[i].rule_id;
81 		ruleset.rules[i].subset_id = rules[i].group_id;
82 		ruleset.rules[i].rule_direction_type =
83 				RXP_RULE_DIRECTION_TYPE_NONE;
84 	}
85 
86 	ret = rxp_compile_advanced(
87 			/*INPUT*/
88 			&ruleset,
89 			prefix_selection_control_list,
90 			rof_for_incremental_compile,
91 			roff_for_incremental_compile,
92 			rofi_for_incremental_compile,
93 			rule_ids_to_remove,
94 			blacklist_sample_data,
95 
96 			/*OPTIONS*/
97 			compiler_options,
98 			prefix_capacity,
99 			global_regex_options,
100 			set_auto_blacklist,
101 			set_max,
102 			objective,
103 			ptpb_threshold,
104 			max_rep_max,
105 			threads,
106 			set_rxp_version,
107 			verbose,
108 			tpe_data_width,
109 			virtual_prefix_mode,
110 			compiler_output_flags,
111 			divide_ruleset,
112 
113 			/*OUTPUT*/
114 			&compilation_statistics,
115 			&compiled_rules_log,
116 			&critical_rules_rank,
117 			&rule_direction_analysis,
118 			&uncompiled_rules_log,
119 			rof,
120 			&roff,
121 			rofi,
122 			&generated_pscl);
123 	rte_free(ruleset.rules);
124 
125 	return ret;
126 }
127 
128 int
otx2_ree_rule_db_compile_prog(struct rte_regexdev * dev)129 otx2_ree_rule_db_compile_prog(struct rte_regexdev *dev)
130 {
131 	struct otx2_ree_data *data = dev->data->dev_private;
132 	char compiler_version[] = "20.5.2.eda0fa2";
133 	char timestamp[] = "19700101_000001";
134 	uint32_t rule_db_len, rule_dbi_len;
135 	struct rxp_rof *rofi_inc_p = NULL;
136 	struct rxp_rof_entry rule_dbi[6];
137 	char *rofi_rof_entries = NULL;
138 	struct rxp_rof *rofi = NULL;
139 	struct rxp_rof *rof = NULL;
140 	struct rxp_rof rofi_inc;
141 	struct rxp_rof rof_inc;
142 	char *rule_db = NULL;
143 	int ret;
144 
145 	ree_func_trace();
146 
147 	ret = otx2_ree_rule_db_len_get(dev, &rule_db_len, &rule_dbi_len);
148 	if (ret != 0) {
149 		otx2_err("Could not get rule db length");
150 		return ret;
151 	}
152 
153 	if (rule_db_len > 0) {
154 		otx2_ree_dbg("Incremental compile, rule db len %d rule dbi len %d",
155 				rule_db_len, rule_dbi_len);
156 		rule_db = rte_malloc("ree_rule_db", rule_db_len, 0);
157 		if (!rule_db) {
158 			otx2_err("Could not allocate memory for rule db");
159 			return -EFAULT;
160 		}
161 
162 		ret = otx2_ree_rule_db_get(dev, rule_db, rule_db_len,
163 				(char *)rule_dbi, rule_dbi_len);
164 		if (ret) {
165 			otx2_err("Could not read rule db");
166 			rte_free(rule_db);
167 			return -EFAULT;
168 		}
169 		rof_inc.rof_revision = 0;
170 		rof_inc.rof_version = 2;
171 		rof_inc.rof_entries = (struct rxp_rof_entry *)rule_db;
172 		rof_inc.rxp_compiler_version = compiler_version;
173 		rof_inc.timestamp = timestamp;
174 		rof_inc.number_of_entries =
175 				(rule_db_len/sizeof(struct rxp_rof_entry));
176 
177 		if (rule_dbi_len > 0) {
178 			/* incremental compilation not the first time */
179 			rofi_inc.rof_revision = 0;
180 			rofi_inc.rof_version = 2;
181 			rofi_inc.rof_entries = rule_dbi;
182 			rofi_inc.rxp_compiler_version = compiler_version;
183 			rofi_inc.timestamp = timestamp;
184 			rofi_inc.number_of_entries =
185 				(rule_dbi_len/sizeof(struct rxp_rof_entry));
186 			rofi_inc_p = &rofi_inc;
187 		}
188 		ret = ree_rule_db_compile(data->rules, data->nb_rules, &rof,
189 				&rofi, &rof_inc, rofi_inc_p);
190 		if (rofi->number_of_entries == 0) {
191 			otx2_ree_dbg("No change to rule db");
192 			ret = 0;
193 			goto free_structs;
194 		}
195 		rule_dbi_len = rofi->number_of_entries *
196 				sizeof(struct rxp_rof_entry);
197 		rofi_rof_entries = (char *)rofi->rof_entries;
198 	} else {
199 		/* full compilation */
200 		ret = ree_rule_db_compile(data->rules, data->nb_rules, &rof,
201 				&rofi, NULL, NULL);
202 	}
203 	if (ret != 0) {
204 		otx2_err("Could not compile rule db");
205 		goto free_structs;
206 	}
207 	rule_db_len = rof->number_of_entries * sizeof(struct rxp_rof_entry);
208 	ret = otx2_ree_rule_db_prog(dev, (char *)rof->rof_entries, rule_db_len,
209 			rofi_rof_entries, rule_dbi_len);
210 	if (ret)
211 		otx2_err("Could not program rule db");
212 
213 free_structs:
214 	rxp_free_structs(NULL, NULL, NULL, NULL, NULL, &rof, NULL, &rofi, NULL,
215 			1);
216 
217 	if (rule_db)
218 		rte_free(rule_db);
219 
220 	return ret;
221 }
222 #else
223 int
otx2_ree_rule_db_compile_prog(struct rte_regexdev * dev)224 otx2_ree_rule_db_compile_prog(struct rte_regexdev *dev)
225 {
226 	RTE_SET_USED(dev);
227 	return -ENOTSUP;
228 }
229 #endif
230