/src/ntopng/fuzz/stub/RedisStub.cpp
Line | Count | Source |
1 | | /* |
2 | | * |
3 | | * (C) 2013-23 - ntop.org |
4 | | * |
5 | | * |
6 | | * This program is free software; you can redistribute it and/or modify |
7 | | * it under the terms of the GNU General Public License as published by |
8 | | * the Free Software Foundation; either version 3 of the License, or |
9 | | * (at your option) any later version. |
10 | | * |
11 | | * This program is distributed in the hope that it will be useful, |
12 | | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
13 | | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
14 | | * GNU General Public License for more details. |
15 | | * |
16 | | * You should have received a copy of the GNU General Public License |
17 | | * along with this program; if not, write to the Free Software Foundation, |
18 | | * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. |
19 | | * |
20 | | */ |
21 | | |
22 | | #include "ntop_includes.h" |
23 | | |
24 | | Redis::Redis(const char *redis_host /* = NULL */, |
25 | | const char *redis_password /* = NULL */, |
26 | | u_int16_t redis_port /* = 0 */, u_int8_t _redis_db_id /* = 0 */, |
27 | 4 | bool giveup_on_failure /* = false */) { |
28 | 4 | this->redisVersion = "RedisStub"; |
29 | 4 | this->localToResolve = |
30 | 4 | std::make_unique<StringFifoQueue>(MAX_NUM_QUEUED_ADDRS); |
31 | 4 | this->remoteToResolve = |
32 | 4 | std::make_unique<StringFifoQueue>(MAX_NUM_QUEUED_ADDRS); |
33 | | |
34 | 4 | memset(&stats, 0, sizeof(stats)); |
35 | 4 | } |
36 | | |
37 | 10.4k | bool Redis::checkList(std::string key) { |
38 | 10.4k | return (this->store.find(key) == this->store.end() && |
39 | 10.4k | this->setStore.find(key) == this->setStore.end()); |
40 | 10.4k | } |
41 | | |
42 | 0 | bool Redis::checkSet(std::string key) { |
43 | 0 | return (this->store.find(key) == this->store.end() && |
44 | 0 | this->listStore.find(key) == this->listStore.end()); |
45 | 0 | } |
46 | | |
47 | 0 | char *Redis::getVersion() { return (char *)this->redisVersion.c_str(); } |
48 | | |
49 | 0 | u_int32_t Redis::getNumVersion() { return 1; } |
50 | | |
51 | 0 | bool Redis::hasRedisDump() { return false; } |
52 | | |
53 | 2 | void Redis::setDefaults() {} |
54 | | |
55 | 20.9k | bool Redis::isOperational() { return true; } |
56 | | |
57 | 2 | void Redis::setInitializationComplete() {} |
58 | | |
59 | 0 | int Redis::info(char *rsp, u_int rsp_len) { |
60 | 0 | if (rsp_len == 0) return -1; |
61 | | |
62 | 0 | stats.num_other++; |
63 | 0 | if(rsp_len == 0) |
64 | 0 | return -1; |
65 | | |
66 | 0 | rsp[0] = 0; |
67 | 0 | return 0; |
68 | 0 | } |
69 | | |
70 | 0 | u_int Redis::dbsize() { |
71 | 0 | stats.num_other++; |
72 | 0 | return this->store.size(); |
73 | 0 | } |
74 | | |
75 | 0 | int Redis::expire(char *key, u_int expire_sec) { |
76 | 0 | stats.num_expire++; |
77 | 0 | return 0; |
78 | 0 | } |
79 | | |
80 | | int Redis::get(char *key, char *rsp, u_int rsp_len, |
81 | 10.5k | bool cache_it /* = false */) { |
82 | 10.5k | if (rsp_len == 0) return -1; |
83 | | |
84 | 10.5k | stats.num_get++; |
85 | 10.5k | std::string strKey(key); |
86 | 10.5k | if (this->store.find(strKey) == this->store.end() || |
87 | 9.79k | snprintf(rsp, rsp_len, "%s", this->store[strKey].c_str()) < 0) { |
88 | 9.79k | rsp[0] = 0; |
89 | 9.79k | return -1; |
90 | 9.79k | } |
91 | | |
92 | 805 | return 0; |
93 | 10.5k | } |
94 | | |
95 | | int Redis::hashGet(const char *key, const char *member, char *const rsp, |
96 | 4 | u_int rsp_len) { |
97 | 4 | if (rsp_len == 0) return -1; |
98 | | |
99 | 4 | std::stringstream ss; |
100 | 4 | ss << key << "@" << member; |
101 | 4 | std::string strKey = ss.str(); |
102 | 4 | if (this->store.find(strKey) == this->store.end() || |
103 | 4 | snprintf(rsp, rsp_len, "%s", this->store[strKey].c_str()) < 0) { |
104 | 4 | rsp[0] = 0; |
105 | 4 | return -1; |
106 | 4 | } |
107 | | |
108 | 0 | return 0; |
109 | 4 | } |
110 | | |
111 | 0 | int Redis::hashDel(const char *key, const char *field) { |
112 | 0 | std::stringstream ss; |
113 | 0 | ss << key << "@" << field; |
114 | 0 | std::string strKey = ss.str(); |
115 | 0 | this->store.erase(strKey); |
116 | 0 | return 0; |
117 | 0 | } |
118 | | |
119 | 4 | int Redis::hashSet(const char *key, const char *field, const char *value) { |
120 | 4 | std::stringstream ss; |
121 | 4 | ss << key << "@" << field; |
122 | 4 | std::string strKey = ss.str(); |
123 | 4 | this->store[strKey] = std::string(value); |
124 | 4 | return 0; |
125 | 4 | } |
126 | | |
127 | | int Redis::set(const char *key, const char *value, |
128 | 1.13k | u_int expire_secs /* = 0 */) { |
129 | 1.13k | std::string strKey(key); |
130 | 1.13k | this->store[strKey] = std::string(value); |
131 | 1.13k | return 0; |
132 | 1.13k | } |
133 | | |
134 | | /* setnx = set if not existing */ |
135 | | int Redis::setnx(const char *key, const char *value, |
136 | 0 | u_int expire_secs /* = 0 */) { |
137 | 0 | std::string strKey(key); |
138 | 0 | if (this->store.find(strKey) != this->store.end()) return -1; |
139 | | |
140 | 0 | this->store[strKey] = std::string(value); |
141 | 0 | return 0; |
142 | 0 | } |
143 | | |
144 | 0 | int Redis::keys(const char *pattern, char ***keys_p) { |
145 | 0 | *keys_p = (char **)malloc(0); |
146 | 0 | return 0; |
147 | 0 | } |
148 | | |
149 | 0 | int Redis::hashKeys(const char *pattern, char ***keys_p) { |
150 | 0 | *keys_p = (char **)malloc(0); |
151 | 0 | return 0; |
152 | 0 | } |
153 | | |
154 | 4 | int Redis::hashGetAll(const char *key, char ***keys_p, char ***values_p) { |
155 | 4 | *keys_p = NULL; |
156 | 4 | return 0; |
157 | 4 | } |
158 | | |
159 | 2 | int Redis::del(char *key) { |
160 | 2 | std::string strKey(key); |
161 | 2 | stats.num_del++; |
162 | 2 | this->store.erase(strKey); |
163 | 2 | return 0; |
164 | 2 | } |
165 | | |
166 | 0 | int Redis::rename(char *key, char *new_key) { |
167 | 0 | return 0; |
168 | 0 | } |
169 | | |
170 | | int Redis::pushHostToResolve(char *hostname, bool dont_check_for_existence, |
171 | 4.25k | bool localHost) { |
172 | 4.25k | if (!ntop->getPrefs()->is_dns_resolution_enabled()) return 0; |
173 | 4.25k | if (hostname == NULL) return -1; |
174 | | |
175 | 4.25k | if (!Utils::shouldResolveHost(hostname)) return -1; |
176 | | |
177 | 4.25k | std::stringstream ss; |
178 | 4.25k | ss << DNS_CACHE << "." << hostname; |
179 | 4.25k | std::string strKey = ss.str(); |
180 | | |
181 | | /* Add only if the address has not been resolved yet */ |
182 | 4.25k | if (dont_check_for_existence || |
183 | 4.25k | this->store.find(strKey) == this->store.end()) { |
184 | 4.25k | auto &q = localHost ? localToResolve : remoteToResolve; |
185 | 4.25k | q->enqueue(hostname); |
186 | | |
187 | 4.25k | return 0; |
188 | 4.25k | } |
189 | | |
190 | 0 | return -1; |
191 | 4.25k | } |
192 | | |
193 | 0 | int Redis::popHostToResolve(char *hostname, u_int hostname_len) { |
194 | 0 | char *item = localToResolve->dequeue(); |
195 | 0 | int rv = -1; |
196 | |
|
197 | 0 | if (!item) item = remoteToResolve->dequeue(); |
198 | |
|
199 | 0 | if (item) { |
200 | 0 | strncpy(hostname, item, hostname_len); |
201 | 0 | hostname[hostname_len - 1] = 0; |
202 | 0 | free(item); |
203 | 0 | rv = 0; |
204 | 0 | } |
205 | |
|
206 | 0 | return rv; |
207 | 0 | } |
208 | | |
209 | | int Redis::getAddress(char *numeric_ip, char *rsp, u_int rsp_len, |
210 | 4.25k | bool queue_if_not_found) { |
211 | 4.25k | if (rsp_len == 0) return -1; |
212 | | |
213 | 4.25k | int rc; |
214 | 4.25k | char key[CONST_MAX_LEN_REDIS_KEY]; |
215 | 4.25k | bool already_in_bloom; |
216 | | |
217 | 4.25k | rsp[0] = 0; |
218 | 4.25k | snprintf(key, sizeof(key), "%s.%s", DNS_CACHE, numeric_ip); |
219 | | |
220 | 4.25k | if (!ntop->getResolutionBloom()->isSetBit(numeric_ip)) { |
221 | 4.25k | already_in_bloom = false; |
222 | 4.25k | rc = -1; /* No way to find it */ |
223 | 4.25k | } else { |
224 | 0 | already_in_bloom = true; |
225 | 0 | rc = this->get(key, rsp, rsp_len); |
226 | 0 | } |
227 | | |
228 | 4.25k | if (rc != 0) { |
229 | 4.25k | if (queue_if_not_found) { |
230 | 4.25k | if (already_in_bloom) |
231 | 0 | ntop->getResolutionBloom()->unsetBit( |
232 | 0 | numeric_ip); /* Expired key ? */ |
233 | | |
234 | 4.25k | this->pushHostToResolve(numeric_ip, true, false); |
235 | 4.25k | } |
236 | 4.25k | } else { |
237 | | /* We need to extend expire */ |
238 | 0 | if (!already_in_bloom) |
239 | 0 | ntop->getResolutionBloom()->setBit( |
240 | 0 | numeric_ip); /* Previously cached ? */ |
241 | |
|
242 | 0 | this->expire(key, DNS_CACHE_DURATION /* expire */); |
243 | 0 | } |
244 | | |
245 | 4.25k | return rc; |
246 | 4.25k | } |
247 | | |
248 | 0 | int Redis::setResolvedAddress(char *numeric_ip, char *symbolic_ip) { |
249 | 0 | char key[CONST_MAX_LEN_REDIS_KEY], numeric[256], *w, *h; |
250 | 0 | int rc = 0; |
251 | |
|
252 | 0 | snprintf(numeric, sizeof(numeric), "%s", numeric_ip); |
253 | |
|
254 | 0 | h = strtok_r(numeric, ";", &w); |
255 | |
|
256 | 0 | while (h != NULL) { |
257 | 0 | snprintf(key, sizeof(key), "%s.%s", DNS_CACHE, h); |
258 | 0 | ntop->getResolutionBloom()->setBit(h); |
259 | 0 | rc = this->set(key, symbolic_ip, DNS_CACHE_DURATION); |
260 | 0 | h = strtok_r(NULL, ";", &w); |
261 | 0 | } |
262 | |
|
263 | 0 | return rc; |
264 | 0 | } |
265 | | |
266 | 0 | int Redis::sadd(const char *set_name, char *item) { |
267 | 0 | std::string strKey(set_name); |
268 | 0 | if (!this->checkSet(strKey)) return -1; |
269 | 0 | if (this->setStore.find(strKey) == this->setStore.end()) |
270 | 0 | this->setStore[strKey] = std::set<std::string>(); |
271 | |
|
272 | 0 | auto result = this->setStore[strKey].insert(std::string(item)); |
273 | 0 | return (result.second ? 1 : 0); |
274 | 0 | } |
275 | | |
276 | 0 | int Redis::srem(const char *set_name, char *item) { |
277 | 0 | std::string strKey(set_name); |
278 | 0 | if (!this->checkSet(strKey)) return -1; |
279 | 0 | if (this->setStore.find(strKey) == this->setStore.end()) return 0; |
280 | | |
281 | 0 | return this->setStore[strKey].erase(std::string(item)); |
282 | 0 | } |
283 | | |
284 | 0 | int Redis::smembers(lua_State *vm, char *setName) { |
285 | 0 | stats.num_other++; |
286 | 0 | std::string strKey(setName); |
287 | 0 | if (!this->checkSet(strKey)) return -1; |
288 | 0 | if (this->setStore.find(strKey) == this->setStore.end()) return 0; |
289 | | |
290 | 0 | int k = 0; |
291 | 0 | const auto &values = this->setStore[strKey]; |
292 | 0 | for (const auto &val : values) { |
293 | 0 | lua_pushstring(vm, val.c_str()); |
294 | 0 | lua_rawseti(vm, -2, k + 1); |
295 | 0 | ++k; |
296 | 0 | } |
297 | |
|
298 | 0 | return 0; |
299 | 0 | } |
300 | | |
301 | 4 | int Redis::smembers(const char *set_name, char ***members) { |
302 | 4 | std::string strKey(set_name); |
303 | 4 | if (this->setStore.find(strKey) == this->setStore.end()) { |
304 | 4 | *members = NULL; |
305 | 4 | return -1; |
306 | 4 | } |
307 | | |
308 | 0 | int k = 0; |
309 | 0 | const auto &values = this->setStore[strKey]; |
310 | 0 | if ((*members = (char **)malloc(values.size() * sizeof(char *))) != NULL) |
311 | 0 | for (auto val : values) (*members)[k++] = strdup(val.c_str()); |
312 | |
|
313 | 0 | return values.size(); |
314 | 4 | } |
315 | | |
316 | 0 | bool Redis::sismember(const char *set_name, const char *member) { |
317 | 0 | stats.num_other++; |
318 | 0 | std::string strKey(set_name); |
319 | 0 | if (this->setStore.find(strKey) == this->setStore.end()) return false; |
320 | | |
321 | 0 | return (this->setStore[strKey].find(std::string(member)) == |
322 | 0 | this->setStore[strKey].end()); |
323 | 0 | } |
324 | | |
325 | | int Redis::lpush(const char *queue_name, const char *msg, u_int queue_trim_size, |
326 | 10.4k | bool trace_errors /* = true */) { |
327 | 10.4k | stats.num_lpush_rpush++; |
328 | 10.4k | std::string strKey(queue_name); |
329 | 10.4k | if (!this->checkList(strKey)) return -1; |
330 | | |
331 | 10.4k | if (this->listStore.find(strKey) == this->listStore.end()) |
332 | 5 | this->listStore[strKey] = std::vector<std::string>(); |
333 | | |
334 | 10.4k | this->listStore[strKey].insert(this->listStore[strKey].begin(), |
335 | 10.4k | std::string(msg)); |
336 | | |
337 | 10.4k | if (queue_trim_size > 0) { |
338 | 10.4k | stats.num_trim++; |
339 | 10.4k | if (this->ltrim(queue_name, -queue_trim_size, -1) == -1) return -1; |
340 | 10.4k | } |
341 | | |
342 | 10.4k | return this->listStore[strKey].size(); |
343 | 10.4k | } |
344 | | |
345 | | int Redis::rpush(const char *queue_name, const char *msg, |
346 | 0 | u_int queue_trim_size) { |
347 | 0 | stats.num_lpush_rpush++; |
348 | 0 | std::string strKey(queue_name); |
349 | 0 | if (!this->checkList(strKey)) return -1; |
350 | | |
351 | 0 | if (this->listStore.find(strKey) == this->listStore.end()) |
352 | 0 | this->listStore[strKey] = std::vector<std::string>(); |
353 | |
|
354 | 0 | this->listStore[strKey].push_back(std::string(msg)); |
355 | |
|
356 | 0 | if (queue_trim_size > 0) { |
357 | 0 | stats.num_trim++; |
358 | 0 | if (this->ltrim(queue_name, -queue_trim_size, -1) == -1) return -1; |
359 | 0 | } |
360 | | |
361 | 0 | return this->listStore[strKey].size(); |
362 | 0 | } |
363 | | |
364 | 0 | int Redis::lindex(const char *queue_name, int idx, char *buf, u_int buf_len) { |
365 | 0 | if (buf_len == 0) return -1; |
366 | 0 | stats.num_other++; |
367 | 0 | std::string strKey(queue_name); |
368 | 0 | if (this->listStore.find(strKey) == this->listStore.end()) { |
369 | 0 | buf[0] = 0; |
370 | 0 | return -1; |
371 | 0 | } |
372 | | |
373 | 0 | const auto &list = this->listStore[strKey]; |
374 | |
|
375 | 0 | if (idx < 0) idx += (int)list.size(); |
376 | 0 | if (idx < 0 || idx >= (int)list.size()) { |
377 | 0 | buf[0] = 0; |
378 | 0 | return -1; |
379 | 0 | } |
380 | | |
381 | 0 | snprintf(buf, buf_len, "%s", list[idx].c_str()); |
382 | |
|
383 | 0 | return 0; |
384 | 0 | } |
385 | | |
386 | 10.4k | int Redis::ltrim(const char *queue_name, int start_idx, int end_idx) { |
387 | 10.4k | stats.num_other++; |
388 | 10.4k | std::string strKey(queue_name); |
389 | 10.4k | if (this->listStore.find(strKey) == this->listStore.end()) return -1; |
390 | | |
391 | 10.4k | auto &list = this->listStore[strKey]; |
392 | 10.4k | if (start_idx < 0) start_idx += list.size(); |
393 | 10.4k | if (end_idx < 0) end_idx += list.size(); |
394 | 10.4k | int k = 0; |
395 | 345k | for (auto it = list.begin(); it != list.end(); ++k) { |
396 | 334k | if (k < start_idx || k > end_idx) |
397 | 0 | list.erase(it); |
398 | 334k | else |
399 | 334k | ++it; |
400 | 334k | } |
401 | | |
402 | 10.4k | return 0; |
403 | 10.4k | } |
404 | | |
405 | 0 | u_int Redis::hstrlen(const char *key, const char *value) { |
406 | 0 | stats.num_other++; |
407 | 0 | std::stringstream ss; |
408 | 0 | ss << key << "@" << value; |
409 | 0 | std::string strKey = ss.str(); |
410 | 0 | if (this->store.find(strKey) == this->store.end()) return 0; |
411 | | |
412 | 0 | return this->store[strKey].size(); |
413 | 0 | } |
414 | | |
415 | 841 | u_int Redis::len(const char *key) { |
416 | 841 | std::string strKey(key); |
417 | 841 | if (this->store.find(strKey) == this->store.end()) return 0; |
418 | | |
419 | 735 | return this->store[strKey].size(); |
420 | 841 | } |
421 | | |
422 | 10.4k | u_int Redis::llen(const char *queue_name) { |
423 | 10.4k | stats.num_llen++; |
424 | 10.4k | std::string strKey(queue_name); |
425 | 10.4k | if (this->listStore.find(strKey) == this->listStore.end()) return 0; |
426 | | |
427 | 10.4k | return this->listStore[strKey].size(); |
428 | 10.4k | } |
429 | | |
430 | 0 | int Redis::lset(const char *queue_name, u_int32_t idx, const char *value) { |
431 | 0 | return -1; |
432 | 0 | } |
433 | | |
434 | 4 | int Redis::lrem(const char *queue_name, const char *value) { |
435 | 4 | stats.num_other++; |
436 | 4 | std::string strKey(queue_name); |
437 | 4 | if (this->listStore.find(strKey) == this->listStore.end()) return 0; |
438 | | |
439 | 0 | for (auto it = this->listStore[strKey].begin(); |
440 | 0 | it != this->listStore[strKey].end();) { |
441 | 0 | if (strncmp(it->c_str(), value, it->size()) == 0) |
442 | 0 | this->listStore[strKey].erase(it); |
443 | 0 | else |
444 | 0 | ++it; |
445 | 0 | } |
446 | 0 | return 0; |
447 | 4 | } |
448 | | |
449 | | int Redis::lrange(const char *list_name, char ***elements, int start_offset, |
450 | 0 | int end_offset) { |
451 | 0 | stats.num_other++; |
452 | 0 | std::string strKey(list_name); |
453 | 0 | if (this->listStore.find(strKey) == this->listStore.end()) return 0; |
454 | | |
455 | 0 | auto &list = this->listStore[strKey]; |
456 | 0 | if (start_offset < 0) start_offset += list.size(); |
457 | 0 | if (end_offset < 0) end_offset += list.size(); |
458 | 0 | int k = 0; |
459 | 0 | vector<std::string> retList; |
460 | 0 | for (auto it = list.begin(); it != list.end(); ++k, ++it) { |
461 | 0 | if (k >= start_offset && k <= end_offset) retList.push_back(*it); |
462 | 0 | } |
463 | |
|
464 | 0 | *elements = (char **)malloc(retList.size() * sizeof(char *)); |
465 | 0 | for (int i = 0; i < (int)retList.size(); ++i) |
466 | 0 | (*elements)[i] = strdup(retList[i].c_str()); |
467 | |
|
468 | 0 | return retList.size(); |
469 | 0 | } |
470 | | |
471 | 0 | int Redis::lpop(const char *queue_name, char *buf, u_int buf_len) { |
472 | 0 | stats.num_lpop_rpop++; |
473 | 0 | std::string strKey(queue_name); |
474 | 0 | if (this->listStore.find(strKey) == this->listStore.end()) { |
475 | 0 | buf[0] = 0; |
476 | 0 | return -1; |
477 | 0 | } |
478 | | |
479 | 0 | if (this->listStore[strKey].size() == 0) { |
480 | 0 | buf[0] = 0; |
481 | 0 | return -1; |
482 | 0 | } |
483 | | |
484 | 0 | snprintf(buf, buf_len, "%s", this->listStore[strKey].front().c_str()); |
485 | 0 | this->listStore[strKey].erase(this->listStore[strKey].begin()); |
486 | |
|
487 | 0 | return 0; |
488 | 0 | } |
489 | | |
490 | 10.4k | int Redis::rpop(const char *queue_name, char *buf, u_int buf_len) { |
491 | 10.4k | stats.num_lpop_rpop++; |
492 | 10.4k | std::string strKey(queue_name); |
493 | 10.4k | if (this->listStore.find(strKey) == this->listStore.end()) { |
494 | 0 | buf[0] = 0; |
495 | 0 | return -1; |
496 | 0 | } |
497 | | |
498 | 10.4k | if (this->listStore[strKey].size() == 0) { |
499 | 0 | buf[0] = 0; |
500 | 0 | return -1; |
501 | 0 | } |
502 | | |
503 | 10.4k | snprintf(buf, buf_len, "%s", this->listStore[strKey].back().c_str()); |
504 | 10.4k | this->listStore[strKey].pop_back(); |
505 | | |
506 | 10.4k | return 0; |
507 | 10.4k | } |
508 | | |
509 | 0 | int Redis::incr(const char *key, int amount) { |
510 | 0 | std::string strKey(key); |
511 | 0 | if (this->store.find(strKey) == this->store.end()) return 0; |
512 | | |
513 | 0 | const auto &val = this->store[strKey]; |
514 | 0 | try { |
515 | 0 | long l = std::stol(val); |
516 | 0 | l += amount; |
517 | 0 | std::stringstream ss; |
518 | 0 | ss << l; |
519 | 0 | this->store[strKey] = ss.str(); |
520 | 0 | return l; |
521 | 0 | } catch (std::exception const &e) { |
522 | 0 | return 0; |
523 | 0 | } |
524 | 0 | } |
525 | | |
526 | 0 | int Redis::flushDb() { |
527 | 0 | stats.num_other++; |
528 | 0 | this->store.clear(); |
529 | 0 | return 0; |
530 | 0 | } |
531 | | |
532 | 0 | void Redis::flushCache() {} |
533 | | |
534 | 0 | void Redis::lua(lua_State *vm) { |
535 | 0 | lua_newtable(vm); |
536 | |
|
537 | 0 | lua_push_uint64_table_entry(vm, "num_expire", stats.num_expire); |
538 | 0 | lua_push_uint64_table_entry(vm, "num_get", stats.num_get); |
539 | 0 | lua_push_uint64_table_entry(vm, "num_ttl", stats.num_ttl); |
540 | 0 | lua_push_uint64_table_entry(vm, "num_del", stats.num_del); |
541 | 0 | lua_push_uint64_table_entry(vm, "num_hget", stats.num_hget); |
542 | 0 | lua_push_uint64_table_entry(vm, "num_hset", stats.num_hset); |
543 | 0 | lua_push_uint64_table_entry(vm, "num_hdel", stats.num_hdel); |
544 | 0 | lua_push_uint64_table_entry(vm, "num_set", stats.num_set); |
545 | 0 | lua_push_uint64_table_entry(vm, "num_expire", stats.num_expire); |
546 | 0 | lua_push_uint64_table_entry(vm, "num_keys", stats.num_keys); |
547 | 0 | lua_push_uint64_table_entry(vm, "num_hkeys", stats.num_hkeys); |
548 | 0 | lua_push_uint64_table_entry(vm, "num_hgetall", stats.num_hgetall); |
549 | 0 | lua_push_uint64_table_entry(vm, "num_trim", stats.num_trim); |
550 | 0 | lua_push_uint64_table_entry(vm, "num_reconnections", |
551 | 0 | stats.num_reconnections); |
552 | 0 | lua_push_uint64_table_entry(vm, "num_lpush_rpush", stats.num_lpush_rpush); |
553 | 0 | lua_push_uint64_table_entry(vm, "num_lpop_rpop", stats.num_lpop_rpop); |
554 | 0 | lua_push_uint64_table_entry(vm, "num_llen", stats.num_llen); |
555 | 0 | lua_push_uint64_table_entry(vm, "num_strlen", stats.num_strlen); |
556 | 0 | lua_push_uint64_table_entry(vm, "num_other", stats.num_other); |
557 | | |
558 | | /* Address resolution */ |
559 | 0 | lua_push_uint64_table_entry(vm, "num_resolver_saved_lookups", |
560 | 0 | stats.num_saved_lookups); |
561 | 0 | lua_push_uint64_table_entry(vm, "num_resolver_get_address", |
562 | 0 | stats.num_get_address); |
563 | 0 | lua_push_uint64_table_entry(vm, "num_resolver_set_address", |
564 | 0 | stats.num_set_resolved_address); |
565 | 0 | } |
566 | | |
567 | 0 | char *Redis::dump(char *key) { |
568 | 0 | stats.num_other++; |
569 | 0 | char *ret = (char *)malloc(1); |
570 | 0 | ret[0] = 0; |
571 | 0 | return ret; |
572 | 0 | } |
573 | | |
574 | 0 | int Redis::restore(char *key, char *buf) { return 0; } |