GNUnet  0.11.x
plugin_datastore_mysql.c
Go to the documentation of this file.
1 /*
2  This file is part of GNUnet
3  Copyright (C) 2009, 2010, 2011 GNUnet e.V.
4 
5  GNUnet is free software: you can redistribute it and/or modify it
6  under the terms of the GNU Affero General Public License as published
7  by the Free Software Foundation, either version 3 of the License,
8  or (at your option) any later version.
9 
10  GNUnet is distributed in the hope that it will be useful, but
11  WITHOUT ANY WARRANTY; without even the implied warranty of
12  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13  Affero General Public License for more details.
14 
15  You should have received a copy of the GNU Affero General Public License
16  along with this program. If not, see <http://www.gnu.org/licenses/>.
17 
18  SPDX-License-Identifier: AGPL3.0-or-later
19  */
20 
120 #include "platform.h"
121 #include "gnunet_datastore_plugin.h"
122 #include "gnunet_util_lib.h"
123 #include "gnunet_mysql_lib.h"
124 #include "gnunet_my_lib.h"
125 
126 #define MAX_DATUM_SIZE 65536
127 
128 
132 struct Plugin
133 {
138 
143 
147 #define INSERT_ENTRY \
148  "INSERT INTO gn090 (repl,type,prio,anonLevel,expire,rvalue,hash,vhash,value) VALUES (?,?,?,?,?,?,?,?,?)"
150 
151 #define DELETE_ENTRY_BY_UID "DELETE FROM gn090 WHERE uid=?"
153 
154 #define DELETE_ENTRY_BY_HASH_VALUE "DELETE FROM gn090 " \
155  "WHERE hash = ? AND " \
156  "value = ? " \
157  "LIMIT 1"
159 
160 #define RESULT_COLUMNS "repl, type, prio, anonLevel, expire, hash, value, uid"
161 
162 #define SELECT_ENTRY "SELECT " RESULT_COLUMNS " FROM gn090 " \
163  "WHERE uid >= ? AND " \
164  "(rvalue >= ? OR 0 = ?) " \
165  "ORDER BY uid LIMIT 1"
167 
168 #define SELECT_ENTRY_BY_HASH "SELECT " RESULT_COLUMNS " FROM gn090 " \
169  "FORCE INDEX (idx_hash_type_uid) " \
170  "WHERE hash=? AND " \
171  "uid >= ? AND " \
172  "(rvalue >= ? OR 0 = ?) " \
173  "ORDER BY uid LIMIT 1"
175 
176 #define SELECT_ENTRY_BY_HASH_AND_TYPE "SELECT " RESULT_COLUMNS " FROM gn090 " \
177  "FORCE INDEX (idx_hash_type_uid) " \
178  "WHERE hash = ? AND " \
179  "type = ? AND " \
180  "uid >= ? AND " \
181  "(rvalue >= ? OR 0 = ?) " \
182  "ORDER BY uid LIMIT 1"
184 
185 #define UPDATE_ENTRY "UPDATE gn090 SET " \
186  "prio = prio + ?, " \
187  "repl = repl + ?, " \
188  "expire = GREATEST(expire, ?) " \
189  "WHERE hash = ? AND vhash = ?"
191 
192 #define DEC_REPL "UPDATE gn090 SET repl=GREATEST (1, repl) - 1 WHERE uid=?"
194 
195 #define SELECT_SIZE "SELECT SUM(LENGTH(value)+256) FROM gn090"
197 
198 #define SELECT_IT_NON_ANONYMOUS "SELECT " RESULT_COLUMNS " FROM gn090 " \
199  "FORCE INDEX (idx_anonLevel_type_rvalue) " \
200  "WHERE anonLevel=0 AND " \
201  "type=? AND " \
202  "uid >= ? " \
203  "ORDER BY uid LIMIT 1"
205 
206 #define SELECT_IT_EXPIRATION "SELECT " RESULT_COLUMNS " FROM gn090 " \
207  "FORCE INDEX (idx_expire) " \
208  "WHERE expire < ? " \
209  "ORDER BY expire ASC LIMIT 1"
211 
212 #define SELECT_IT_PRIORITY "SELECT " RESULT_COLUMNS " FROM gn090 " \
213  "FORCE INDEX (idx_prio) " \
214  "ORDER BY prio ASC LIMIT 1"
216 
217 #define SELECT_IT_REPLICATION "SELECT " RESULT_COLUMNS " FROM gn090 " \
218  "FORCE INDEX (idx_repl_rvalue) " \
219  "WHERE repl=? AND " \
220  " (rvalue>=? OR" \
221  " NOT EXISTS (SELECT 1 FROM gn090 FORCE INDEX (idx_repl_rvalue) WHERE repl=? AND rvalue>=?)) " \
222  "ORDER BY rvalue ASC " \
223  "LIMIT 1"
225 
226 #define SELECT_MAX_REPL "SELECT MAX(repl) FROM gn090"
228 
229 #define GET_ALL_KEYS "SELECT hash from gn090"
231 };
232 
233 #define MAX_PARAM 16
234 
242 static int
244  unsigned long long uid)
245 {
246  int ret;
247  uint64_t uid64 = (uint64_t) uid;
248  struct GNUNET_MY_QueryParam params_delete[] = {
251  };
252 
254  "Deleting value %llu from gn090 table\n",
255  uid);
256  ret = GNUNET_MY_exec_prepared (plugin->mc,
257  plugin->delete_entry_by_uid,
258  params_delete);
259  if (ret >= 0)
260  {
261  return GNUNET_OK;
262  }
264  "Deleting value %llu from gn090 table failed\n",
265  (unsigned long long) uid);
266  return ret;
267 }
268 
269 
277 static void
279  unsigned long long *estimate)
280 {
281  struct Plugin *plugin = cls;
282  uint64_t total;
283  int ret;
284  struct GNUNET_MY_QueryParam params_get[] = {
286  };
287  struct GNUNET_MY_ResultSpec results_get[] = {
290  };
291 
292  ret = GNUNET_MY_exec_prepared (plugin->mc,
293  plugin->get_size,
294  params_get);
295  *estimate = 0;
296  total = UINT64_MAX;
297  if ((GNUNET_OK == ret) &&
298  (GNUNET_OK ==
300  results_get)))
301  {
302  *estimate = (unsigned long long) total;
304  "Size estimate for MySQL payload is %lld\n",
305  (long long) total);
306  GNUNET_assert (UINT64_MAX != total);
309  NULL));
310  }
311 }
312 
313 
330 static void
331 mysql_plugin_put (void *cls,
332  const struct GNUNET_HashCode *key,
333  bool absent,
334  uint32_t size,
335  const void *data,
336  enum GNUNET_BLOCK_Type type,
337  uint32_t priority,
338  uint32_t anonymity,
339  uint32_t replication,
341  PluginPutCont cont,
342  void *cont_cls)
343 {
344  struct Plugin *plugin = cls;
345  uint64_t lexpiration = expiration.abs_value_us;
346  struct GNUNET_HashCode vhash;
347 
348  GNUNET_CRYPTO_hash (data,
349  size,
350  &vhash);
351  if (! absent)
352  {
353  struct GNUNET_MY_QueryParam params_update[] = {
354  GNUNET_MY_query_param_uint32 (&priority),
355  GNUNET_MY_query_param_uint32 (&replication),
356  GNUNET_MY_query_param_uint64 (&lexpiration),
360  };
361 
362  if (GNUNET_OK !=
363  GNUNET_MY_exec_prepared (plugin->mc,
364  plugin->update_entry,
365  params_update))
366  {
367  cont (cont_cls,
368  key,
369  size,
371  _ ("MySQL statement run failure"));
372  return;
373  }
374 
375  MYSQL_STMT *stmt = GNUNET_MYSQL_statement_get_stmt (plugin->update_entry);
376  my_ulonglong rows = mysql_stmt_affected_rows (stmt);
377 
380  NULL));
381  if (0 != rows)
382  {
383  cont (cont_cls,
384  key,
385  size,
386  GNUNET_NO,
387  NULL);
388  return;
389  }
390  }
391 
393  UINT64_MAX);
394  struct GNUNET_MY_QueryParam params_insert[] = {
395  GNUNET_MY_query_param_uint32 (&replication),
397  GNUNET_MY_query_param_uint32 (&priority),
398  GNUNET_MY_query_param_uint32 (&anonymity),
399  GNUNET_MY_query_param_uint64 (&lexpiration),
400  GNUNET_MY_query_param_uint64 (&lrvalue),
405  };
406 
407  if (size > MAX_DATUM_SIZE)
408  {
409  GNUNET_break (0);
410  cont (cont_cls, key, size, GNUNET_SYSERR, _ ("Data too large"));
411  return;
412  }
413 
414  if (GNUNET_OK !=
415  GNUNET_MY_exec_prepared (plugin->mc,
416  plugin->insert_entry,
417  params_insert))
418  {
419  cont (cont_cls,
420  key,
421  size,
423  _ ("MySQL statement run failure"));
424  return;
425  }
427  "Inserted value `%s' with size %u into gn090 table\n",
428  GNUNET_h2s (key),
429  (unsigned int) size);
430  if (size > 0)
431  plugin->env->duc (plugin->env->cls,
432  size);
435  NULL));
436  cont (cont_cls,
437  key,
438  size,
439  GNUNET_OK,
440  NULL);
441 }
442 
443 
454 static void
456  struct GNUNET_MYSQL_StatementHandle *stmt,
458  void *proc_cls,
459  struct GNUNET_MY_QueryParam *params_select)
460 {
461  int ret;
462  uint32_t replication;
463  uint32_t type;
464  uint32_t priority;
465  uint32_t anonymity;
466  uint64_t uid;
467  size_t value_size;
468  void *value;
469  struct GNUNET_HashCode key;
470  struct GNUNET_TIME_Absolute expiration;
471  struct GNUNET_MY_ResultSpec results_select[] = {
472  GNUNET_MY_result_spec_uint32 (&replication),
474  GNUNET_MY_result_spec_uint32 (&priority),
475  GNUNET_MY_result_spec_uint32 (&anonymity),
478  GNUNET_MY_result_spec_variable_size (&value, &value_size),
481  };
482 
483  ret = GNUNET_MY_exec_prepared (plugin->mc,
484  stmt,
485  params_select);
486  if (GNUNET_OK != ret)
487  {
488  proc (proc_cls,
489  NULL, 0, NULL, 0, 0, 0, 0, GNUNET_TIME_UNIT_ZERO_ABS, 0);
490  return;
491  }
492 
493  ret = GNUNET_MY_extract_result (stmt,
494  results_select);
495  if (GNUNET_OK != ret)
496  {
497  proc (proc_cls,
498  NULL, 0, NULL, 0, 0, 0, 0, GNUNET_TIME_UNIT_ZERO_ABS, 0);
499  return;
500  }
501 
503  "Found %u-byte value under key `%s' with prio %u, anon %u, expire %s selecting from gn090 table\n",
504  (unsigned int) value_size,
505  GNUNET_h2s (&key),
506  (unsigned int) priority,
507  (unsigned int) anonymity,
509  GNUNET_assert (value_size < MAX_DATUM_SIZE);
512  NULL));
513  ret = proc (proc_cls,
514  &key,
515  value_size,
516  value,
517  type,
518  priority,
519  anonymity,
520  replication,
521  expiration,
522  uid);
523  GNUNET_MY_cleanup_result (results_select);
524  if (GNUNET_NO == ret)
525  {
526  do_delete_entry (plugin, uid);
527  if (0 != value_size)
528  plugin->env->duc (plugin->env->cls,
529  -value_size);
530  }
531 }
532 
533 
547 static void
549  uint64_t next_uid,
550  bool random,
551  const struct GNUNET_HashCode *key,
552  enum GNUNET_BLOCK_Type type,
554  void *proc_cls)
555 {
556  struct Plugin *plugin = cls;
557  uint64_t rvalue;
558 
559  if (random)
560  {
562  UINT64_MAX);
563  next_uid = 0;
564  }
565  else
566  rvalue = 0;
567 
568  if (NULL == key)
569  {
570  struct GNUNET_MY_QueryParam params_select[] = {
571  GNUNET_MY_query_param_uint64 (&next_uid),
575  };
576 
577  execute_select (plugin,
578  plugin->select_entry,
579  proc,
580  proc_cls,
581  params_select);
582  }
583  else if (type != GNUNET_BLOCK_TYPE_ANY)
584  {
585  struct GNUNET_MY_QueryParam params_select[] = {
588  GNUNET_MY_query_param_uint64 (&next_uid),
592  };
593 
594  execute_select (plugin,
596  proc,
597  proc_cls,
598  params_select);
599  }
600  else
601  {
602  struct GNUNET_MY_QueryParam params_select[] = {
604  GNUNET_MY_query_param_uint64 (&next_uid),
608  };
609 
610  execute_select (plugin,
611  plugin->select_entry_by_hash,
612  proc,
613  proc_cls,
614  params_select);
615  }
616 }
617 
618 
630 static void
632  uint64_t next_uid,
633  enum GNUNET_BLOCK_Type type,
635  void *proc_cls)
636 {
637  struct Plugin *plugin = cls;
638  uint32_t typei = (uint32_t) type;
639 
640  struct GNUNET_MY_QueryParam params_zero_iter[] = {
642  GNUNET_MY_query_param_uint64 (&next_uid),
644  };
645 
646  execute_select (plugin,
647  plugin->zero_iter,
648  proc,
649  proc_cls,
650  params_zero_iter);
651 }
652 
653 
657 struct ReplCtx
658 {
662  struct Plugin *plugin;
663 
668 
672  void *proc_cls;
673 };
674 
675 
696 static int
697 repl_proc (void *cls,
698  const struct GNUNET_HashCode *key,
699  uint32_t size,
700  const void *data,
701  enum GNUNET_BLOCK_Type type,
702  uint32_t priority,
703  uint32_t anonymity,
704  uint32_t replication,
706  uint64_t uid)
707 {
708  struct ReplCtx *rc = cls;
709  struct Plugin *plugin = rc->plugin;
710  int ret;
711  int iret;
712 
713  ret = rc->proc (rc->proc_cls,
714  key,
715  size,
716  data,
717  type,
718  priority,
719  anonymity,
720  replication,
721  expiration,
722  uid);
723  if (NULL != key)
724  {
725  struct GNUNET_MY_QueryParam params_proc[] = {
728  };
729 
730  iret = GNUNET_MY_exec_prepared (plugin->mc,
731  plugin->dec_repl,
732  params_proc);
733  if (GNUNET_SYSERR == iret)
734  {
736  "Failed to reduce replication counter\n");
737  return GNUNET_SYSERR;
738  }
739  }
740  return ret;
741 }
742 
743 
755 static void
758  void *proc_cls)
759 {
760  struct Plugin *plugin = cls;
761  uint64_t rvalue;
762  uint32_t repl;
763  struct ReplCtx rc;
764  struct GNUNET_MY_QueryParam params_get[] = {
766  };
767  struct GNUNET_MY_ResultSpec results_get[] = {
770  };
771  struct GNUNET_MY_QueryParam params_select[] = {
777  };
778 
779  rc.plugin = plugin;
780  rc.proc = proc;
781  rc.proc_cls = proc_cls;
782 
783  if (1 !=
784  GNUNET_MY_exec_prepared (plugin->mc,
785  plugin->max_repl,
786  params_get))
787  {
788  proc (proc_cls, NULL, 0, NULL, 0, 0, 0, 0, GNUNET_TIME_UNIT_ZERO_ABS, 0);
789  return;
790  }
791 
792  if (GNUNET_OK !=
794  results_get))
795  {
796  proc (proc_cls, NULL, 0, NULL, 0, 0, 0, 0, GNUNET_TIME_UNIT_ZERO_ABS, 0);
797  return;
798  }
801  NULL));
803  UINT64_MAX);
804 
805  execute_select (plugin,
806  plugin->select_replication,
807  &repl_proc,
808  &rc,
809  params_select);
810 }
811 
812 
820 static void
822  PluginKeyProcessor proc,
823  void *proc_cls)
824 {
825  struct Plugin *plugin = cls;
826  int ret;
827  MYSQL_STMT *statement;
828  unsigned int cnt;
829  struct GNUNET_HashCode key;
830  struct GNUNET_HashCode last;
831  struct GNUNET_MY_QueryParam params_select[] = {
833  };
834  struct GNUNET_MY_ResultSpec results_select[] = {
837  };
838 
839  GNUNET_assert (NULL != proc);
840  statement = GNUNET_MYSQL_statement_get_stmt (plugin->get_all_keys);
841  if (GNUNET_OK !=
842  GNUNET_MY_exec_prepared (plugin->mc,
843  plugin->get_all_keys,
844  params_select))
845  {
847  _ ("`%s' for `%s' failed at %s:%d with error: %s\n"),
848  "mysql_stmt_execute",
849  GET_ALL_KEYS,
850  __FILE__,
851  __LINE__,
852  mysql_stmt_error (statement));
854  proc (proc_cls, NULL, 0);
855  return;
856  }
857  memset (&last, 0, sizeof(last)); /* make static analysis happy */
858  ret = GNUNET_YES;
859  cnt = 0;
860  while (ret == GNUNET_YES)
861  {
862  ret = GNUNET_MY_extract_result (plugin->get_all_keys,
863  results_select);
864  if (0 != GNUNET_memcmp (&last,
865  &key))
866  {
867  if (0 != cnt)
868  proc (proc_cls,
869  &last,
870  cnt);
871  cnt = 1;
872  last = key;
873  }
874  else
875  {
876  cnt++;
877  }
878  }
879  if (0 != cnt)
880  proc (proc_cls,
881  &last,
882  cnt);
883  /* finally, let app know we are done */
884  proc (proc_cls,
885  NULL,
886  0);
887  if (GNUNET_SYSERR == ret)
888  {
890  _ ("`%s' failed at %s:%d with error: %s\n"),
891  "mysql_stmt_fetch",
892  __FILE__,
893  __LINE__,
894  mysql_stmt_error (statement));
896  return;
897  }
898 }
899 
900 
904 struct ExpiCtx
905 {
909  struct Plugin *plugin;
910 
915 
919  void *proc_cls;
920 };
921 
922 
943 static int
944 expi_proc (void *cls,
945  const struct GNUNET_HashCode *key,
946  uint32_t size,
947  const void *data,
948  enum GNUNET_BLOCK_Type type,
949  uint32_t priority,
950  uint32_t anonymity,
951  uint32_t replication,
953  uint64_t uid)
954 {
955  struct ExpiCtx *rc = cls;
956  struct Plugin *plugin = rc->plugin;
957  struct GNUNET_MY_QueryParam params_select[] = {
959  };
960 
961  if (NULL == key)
962  {
963  execute_select (plugin,
964  plugin->select_priority,
965  rc->proc,
966  rc->proc_cls,
967  params_select);
968  return GNUNET_SYSERR;
969  }
970  return rc->proc (rc->proc_cls,
971  key,
972  size,
973  data,
974  type,
975  priority,
976  anonymity,
977  replication,
978  expiration,
979  uid);
980 }
981 
982 
991 static void
994  void *proc_cls)
995 {
996  struct Plugin *plugin = cls;
997  struct GNUNET_TIME_Absolute now;
998  struct GNUNET_MY_QueryParam params_select[] = {
1001  };
1002  struct ExpiCtx rc;
1003 
1004  rc.plugin = plugin;
1005  rc.proc = proc;
1006  rc.proc_cls = proc_cls;
1007  now = GNUNET_TIME_absolute_get ();
1008  execute_select (plugin,
1009  plugin->select_expiration,
1010  expi_proc,
1011  &rc,
1012  params_select);
1013 }
1014 
1015 
1021 static void
1023 {
1024  struct Plugin *plugin = cls;
1025 
1026  if (GNUNET_OK !=
1027  GNUNET_MYSQL_statement_run (plugin->mc,
1028  "DROP TABLE gn090"))
1029  return; /* error */
1030  plugin->env->duc (plugin->env->cls, 0);
1031 }
1032 
1033 
1044 static void
1046  const struct GNUNET_HashCode *key,
1047  uint32_t size,
1048  const void *data,
1049  PluginRemoveCont cont,
1050  void *cont_cls)
1051 {
1052  struct Plugin *plugin = cls;
1053  struct GNUNET_MY_QueryParam params_delete[] = {
1055  GNUNET_MY_query_param_fixed_size (data, size),
1057  };
1058 
1059  if (GNUNET_OK !=
1060  GNUNET_MY_exec_prepared (plugin->mc,
1062  params_delete))
1063  {
1065  "Removing key `%s' from gn090 table failed\n",
1066  GNUNET_h2s (key));
1067  cont (cont_cls,
1068  key,
1069  size,
1070  GNUNET_SYSERR,
1071  _ ("MySQL statement run failure"));
1072  return;
1073  }
1074 
1075  MYSQL_STMT *stmt = GNUNET_MYSQL_statement_get_stmt (
1076  plugin->delete_entry_by_hash_value);
1077  my_ulonglong rows = mysql_stmt_affected_rows (stmt);
1078 
1079  if (0 == rows)
1080  {
1081  cont (cont_cls,
1082  key,
1083  size,
1084  GNUNET_NO,
1085  NULL);
1086  return;
1087  }
1088  plugin->env->duc (plugin->env->cls,
1089  -size);
1090  cont (cont_cls,
1091  key,
1092  size,
1093  GNUNET_OK,
1094  NULL);
1095 }
1096 
1097 
1104 void *
1106 {
1109  struct Plugin *plugin;
1110 
1111  plugin = GNUNET_new (struct Plugin);
1112  plugin->env = env;
1113  plugin->mc = GNUNET_MYSQL_context_create (env->cfg,
1114  "datastore-mysql");
1115  if (NULL == plugin->mc)
1116  {
1117  GNUNET_free (plugin);
1118  return NULL;
1119  }
1120 #define MRUNS(a) (GNUNET_OK != GNUNET_MYSQL_statement_run (plugin->mc, a))
1121 #define PINIT(a, b) (NULL == (a = GNUNET_MYSQL_statement_prepare (plugin->mc, \
1122  b)))
1123  if (MRUNS
1124  ("CREATE TABLE IF NOT EXISTS gn090 ("
1125  " repl INT(11) UNSIGNED NOT NULL DEFAULT 0,"
1126  " type INT(11) UNSIGNED NOT NULL DEFAULT 0,"
1127  " prio INT(11) UNSIGNED NOT NULL DEFAULT 0,"
1128  " anonLevel INT(11) UNSIGNED NOT NULL DEFAULT 0,"
1129  " expire BIGINT UNSIGNED NOT NULL DEFAULT 0,"
1130  " rvalue BIGINT UNSIGNED NOT NULL,"
1131  " hash BINARY(64) NOT NULL DEFAULT '',"
1132  " vhash BINARY(64) NOT NULL DEFAULT '',"
1133  " value BLOB NOT NULL DEFAULT '',"
1134  " uid BIGINT NOT NULL AUTO_INCREMENT,"
1135  " PRIMARY KEY (uid),"
1136  " INDEX idx_hash_type_uid (hash(64),type,rvalue),"
1137  " INDEX idx_prio (prio),"
1138  " INDEX idx_repl_rvalue (repl,rvalue),"
1139  " INDEX idx_expire (expire),"
1140  " INDEX idx_anonLevel_type_rvalue (anonLevel,type,rvalue)"
1141  ") ENGINE=InnoDB") || MRUNS ("SET AUTOCOMMIT = 1") ||
1142  PINIT (plugin->insert_entry, INSERT_ENTRY) ||
1145  PINIT (plugin->select_entry, SELECT_ENTRY) ||
1149  PINIT (plugin->get_size, SELECT_SIZE) ||
1150  PINIT (plugin->update_entry, UPDATE_ENTRY) ||
1151  PINIT (plugin->dec_repl, DEC_REPL) ||
1155  PINIT (plugin->max_repl, SELECT_MAX_REPL) ||
1156  PINIT (plugin->get_all_keys, GET_ALL_KEYS) ||
1158  false)
1159  {
1160  GNUNET_MYSQL_context_destroy (plugin->mc);
1161  GNUNET_free (plugin);
1162  return NULL;
1163  }
1164 #undef PINIT
1165 #undef MRUNS
1166 
1168  api->cls = plugin;
1170  api->put = &mysql_plugin_put;
1171  api->get_key = &mysql_plugin_get_key;
1176  api->drop = &mysql_plugin_drop;
1179  _ ("Mysql database running\n"));
1180  return api;
1181 }
1182 
1183 
1190 void *
1192 {
1194  struct Plugin *plugin = api->cls;
1195 
1196  GNUNET_MYSQL_context_destroy (plugin->mc);
1197  GNUNET_free (plugin);
1198  GNUNET_free (api);
1199  return NULL;
1200 }
1201 
1202 
1203 /* end of plugin_datastore_mysql.c */
struct GNUNET_MYSQL_Context * mc
Handle to talk to MySQL.
struct GNUNET_MYSQL_StatementHandle * select_entry_by_hash_and_type
struct GNUNET_MYSQL_StatementHandle * select_expiration
PluginGetKeys get_keys
Iterate over all keys in the database.
PluginPut put
Function to store an item in the datastore.
#define GNUNET_MY_query_param_auto_from_type(x)
Generate fixed-size query parameter with size determined by variable type.
int(* PluginDatumProcessor)(void *cls, const struct GNUNET_HashCode *key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, uint32_t replication, struct GNUNET_TIME_Absolute expiration, uint64_t uid)
An processor over a set of items stored in the datastore.
#define PINIT(a, b)
void * proc_cls
Closure for proc.
PluginGetType get_zero_anonymity
Get datum (of the specified type) with anonymity level zero.
struct GNUNET_MY_QueryParam GNUNET_MY_query_param_uint64(const uint64_t *x)
Generate query parameter for an uint64_t in host byte order.
struct Plugin * plugin
Plugin handle.
#define GNUNET_TIME_UNIT_ZERO_ABS
Absolute time zero.
#define MRUNS(a)
void * proc_cls
Closure for proc.
struct GNUNET_MYSQL_StatementHandle * insert_entry
struct GNUNET_MYSQL_Context * GNUNET_MYSQL_context_create(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section)
Create a mysql context.
Definition: mysql.c:320
Any type of block, used as a wildcard when searching.
#define SELECT_IT_EXPIRATION
#define UPDATE_ENTRY
#define GNUNET_MY_result_spec_end
End of result speceter specification.
GNUNET_BLOCK_Type
Blocks in the datastore and the datacache must have a unique type.
struct GNUNET_MY_ResultSpec GNUNET_MY_result_spec_uint64(uint64_t *u64)
uint64_t expected.
struct GNUNET_MY_QueryParam GNUNET_MY_query_param_fixed_size(const void *ptr, size_t ptr_size)
Generate query parameter for a buffer ptr of ptr_size bytes.FG.
uint64_t GNUNET_CRYPTO_random_u64(enum GNUNET_CRYPTO_Quality mode, uint64_t max)
Random on unsigned 64-bit values.
struct GNUNET_MYSQL_StatementHandle * delete_entry_by_hash_value
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
#define SELECT_IT_REPLICATION
static void mysql_plugin_get_keys(void *cls, PluginKeyProcessor proc, void *proc_cls)
Get all of the keys in the datastore.
void * libgnunet_plugin_datastore_mysql_done(void *cls)
Exit point from the plugin.
struct GNUNET_MYSQL_StatementHandle * delete_entry_by_uid
PluginRemoveKey remove_key
Function to remove an item from the database.
char * key
TLS key.
struct GNUNET_MY_QueryParam GNUNET_MY_query_param_absolute_time(const struct GNUNET_TIME_Absolute *x)
Generate query parameter for an absolute time value.
static unsigned int replication
Information we pass to GNUNET_MY_exec_prepared() to initialize the arguments of the prepared statemen...
Definition: gnunet_my_lib.h:83
PluginEstimateSize estimate_size
Calculate the current on-disk size of the SQ store.
static int ret
Return value of the commandline.
Definition: gnunet-abd.c:81
#define SELECT_IT_PRIORITY
static int repl_proc(void *cls, const struct GNUNET_HashCode *key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, uint32_t replication, struct GNUNET_TIME_Absolute expiration, uint64_t uid)
Wrapper for the processor for mysql_plugin_get_replication().
#define GNUNET_NO
Definition: gnunet_common.h:78
struct GNUNET_MY_ResultSpec GNUNET_MY_result_spec_absolute_time(struct GNUNET_TIME_Absolute *at)
Absolute time expected.
const char * GNUNET_h2s(const struct GNUNET_HashCode *hc)
Convert a hash value to a string (for printing debug messages).
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
struct GNUNET_MYSQL_StatementHandle * zero_iter
#define GNUNET_new(type)
Allocate a struct or union of the given type.
Handle for a prepared statement.
Definition: mysql.c:112
void * libgnunet_plugin_datastore_mysql_init(void *cls)
Entry point for the plugin.
int GNUNET_MY_exec_prepared(struct GNUNET_MYSQL_Context *mc, struct GNUNET_MYSQL_StatementHandle *sh, struct GNUNET_MY_QueryParam *params)
Run a prepared SELECT statement.
Definition: my.c:42
static void mysql_plugin_remove_key(void *cls, const struct GNUNET_HashCode *key, uint32_t size, const void *data, PluginRemoveCont cont, void *cont_cls)
Remove a particular key in the datastore.
void(* PluginPutCont)(void *cls, const struct GNUNET_HashCode *key, uint32_t size, int status, const char *msg)
Put continuation.
uint64_t abs_value_us
The actual value.
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur...
#define DELETE_ENTRY_BY_UID
struct GNUNET_BLOCK_PluginFunctions * api
Plugin API.
Definition: block.c:47
#define SELECT_SIZE
#define _(String)
GNU gettext support macro.
Definition: platform.h:181
PluginGetRandom get_replication
Function to get a random item with high replication score from the database, lowering the item&#39;s repl...
static int expi_proc(void *cls, const struct GNUNET_HashCode *key, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, uint32_t replication, struct GNUNET_TIME_Absolute expiration, uint64_t uid)
Wrapper for the processor for mysql_plugin_get_expiration().
PluginDrop drop
Delete the database.
Information we pass to GNUNET_MY_extract_result() to initialize the arguments of the prepared stateme...
static void mysql_plugin_get_key(void *cls, uint64_t next_uid, bool random, const struct GNUNET_HashCode *key, enum GNUNET_BLOCK_Type type, PluginDatumProcessor proc, void *proc_cls)
Get one of the results for a particular key in the datastore.
static void mysql_plugin_drop(void *cls)
Drop database.
#define DEC_REPL
#define DELETE_ENTRY_BY_HASH_VALUE
static char * value
Value of the record to add/remove.
void GNUNET_CRYPTO_hash(const void *block, size_t size, struct GNUNET_HashCode *ret)
Compute hash of a given block.
Definition: crypto_hash.c:48
void(* PluginKeyProcessor)(void *cls, const struct GNUNET_HashCode *key, unsigned int count)
An processor over a set of keys stored in the datastore.
PluginGetRandom get_expiration
Function to get a random expired item or, if none are expired, either the oldest entry or one with a ...
struct GNUNET_DATACACHE_PluginEnvironment * env
Our execution environment.
void GNUNET_MYSQL_context_destroy(struct GNUNET_MYSQL_Context *mc)
Destroy a mysql context.
Definition: mysql.c:368
#define SELECT_MAX_REPL
Each plugin is required to return a pointer to a struct of this type as the return value from its ent...
#define INSERT_ENTRY
Prepared statements.
void GNUNET_MY_cleanup_result(struct GNUNET_MY_ResultSpec *rs)
Free all memory that was allocated in rs during GNUNET_MY_extract_result().
Definition: my.c:257
Context for expi_proc() function.
MYSQL_STMT * GNUNET_MYSQL_statement_get_stmt(struct GNUNET_MYSQL_StatementHandle *sh)
Get internal handle for a prepared statement.
Definition: mysql.c:478
void GNUNET_MYSQL_statements_invalidate(struct GNUNET_MYSQL_Context *mc)
Close database connection and all prepared statements (we got a DB error).
Definition: mysql.c:341
struct GNUNET_MYSQL_StatementHandle * dec_repl
#define SELECT_ENTRY_BY_HASH_AND_TYPE
PluginDatumProcessor proc
Function to call for the result (or the NULL).
struct GNUNET_MYSQL_StatementHandle * max_repl
The datastore service will pass a pointer to a struct of this type as the first and only argument to ...
A 512-bit hashcode.
#define GET_ALL_KEYS
static char * expiration
Credential TTL.
Definition: gnunet-abd.c:96
static char * plugin
Solver plugin name as string.
struct GNUNET_TIME_Absolute GNUNET_TIME_absolute_get(void)
Get the current time.
Definition: time.c:118
int GNUNET_MY_extract_result(struct GNUNET_MYSQL_StatementHandle *sh, struct GNUNET_MY_ResultSpec *specs)
Extract results from a query result according to the given specification.
Definition: my.c:136
#define SELECT_ENTRY_BY_HASH
static void mysql_plugin_estimate_size(void *cls, unsigned long long *estimate)
Get an estimate of how much space the database is currently using.
struct GNUNET_MYSQL_StatementHandle * get_all_keys
struct GNUNET_MYSQL_StatementHandle * select_priority
#define GNUNET_MY_result_spec_auto_from_type(dst)
We expect a fixed-size result, with size determined by the type of * dst
#define GNUNET_MY_query_param_end
End of query parameter specification.
#define GNUNET_SYSERR
Definition: gnunet_common.h:76
Context for repl_proc() function.
struct GNUNET_MYSQL_StatementHandle * select_entry_by_hash
struct GNUNET_MY_ResultSpec GNUNET_MY_result_spec_uint32(uint32_t *u32)
uint32_t expected
Mysql context.
Definition: mysql.c:75
void(* PluginRemoveCont)(void *cls, const struct GNUNET_HashCode *key, uint32_t size, int status, const char *msg)
Remove continuation.
void * cls
Closure to use for all of the following callbacks (except "next_request").
#define GNUNET_memcmp(a, b)
Compare memory in a and b, where both must be of the same pointer type.
struct GNUNET_MY_QueryParam GNUNET_MY_query_param_uint32(const uint32_t *x)
Generate query parameter for an uint32_t in host byte order.
struct GNUNET_MYSQL_StatementHandle * select_entry
unsigned long long size
Size of all values we&#39;re storing.
Handle for a plugin.
Definition: block.c:37
int GNUNET_MYSQL_statement_run(struct GNUNET_MYSQL_Context *mc, const char *sql)
Run a SQL statement.
Definition: mysql.c:415
static void mysql_plugin_put(void *cls, const struct GNUNET_HashCode *key, bool absent, uint32_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, uint32_t replication, struct GNUNET_TIME_Absolute expiration, PluginPutCont cont, void *cont_cls)
Store an item in the datastore.
struct Plugin * plugin
Plugin handle.
PluginDatumProcessor proc
Function to call for the result (or the NULL).
#define GNUNET_log(kind,...)
#define MAX_DATUM_SIZE
struct GNUNET_MYSQL_StatementHandle * get_size
static void mysql_plugin_get_replication(void *cls, PluginDatumProcessor proc, void *proc_cls)
Get a random item for replication.
void * cls
Closure to use for callbacks.
enum GNUNET_TESTBED_UnderlayLinkModelType type
the type of this model
Time for absolute times used by GNUnet, in microseconds.
#define GNUNET_YES
Definition: gnunet_common.h:77
static void mysql_plugin_get_expiration(void *cls, PluginDatumProcessor proc, void *proc_cls)
Get a random item for expiration.
static unsigned int anonymity
#define SELECT_IT_NON_ANONYMOUS
const char * GNUNET_STRINGS_absolute_time_to_string(struct GNUNET_TIME_Absolute t)
Like asctime, except for GNUnet time.
Definition: strings.c:742
#define GNUNET_log_from(kind, comp,...)
PluginGetKey get_key
Get a particular datum matching a given hash from the datastore.
struct GNUNET_MYSQL_StatementHandle * update_entry
uint32_t data
The data value.
static void mysql_plugin_get_zero_anonymity(void *cls, uint64_t next_uid, enum GNUNET_BLOCK_Type type, PluginDatumProcessor proc, void *proc_cls)
Get a zero-anonymity datum from the datastore.
struct GNUNET_MYSQL_StatementHandle * select_replication
struct GNUNET_MY_ResultSpec GNUNET_MY_result_spec_variable_size(void **dst, size_t *ptr_size)
Variable-size result expected.
No good quality of the operation is needed (i.e., random numbers can be pseudo-random).
const struct GNUNET_CONFIGURATION_Handle * cfg
Configuration to use.
#define GNUNET_free(ptr)
Wrapper around free.
static int do_delete_entry(struct Plugin *plugin, unsigned long long uid)
Delete an entry from the gn090 table.
#define SELECT_ENTRY
static void execute_select(struct Plugin *plugin, struct GNUNET_MYSQL_StatementHandle *stmt, PluginDatumProcessor proc, void *proc_cls, struct GNUNET_MY_QueryParam *params_select)
Run the given select statement and call &#39;proc&#39; on the resulting values (which must be in particular p...