gnunet-namecache.c 6.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245
  1. /*
  2. This file is part of GNUnet.
  3. Copyright (C) 2012, 2013 GNUnet e.V.
  4. GNUnet is free software: you can redistribute it and/or modify it
  5. under the terms of the GNU Affero General Public License as published
  6. by the Free Software Foundation, either version 3 of the License,
  7. or (at your option) any later version.
  8. GNUnet is distributed in the hope that it will be useful, but
  9. WITHOUT ANY WARRANTY; without even the implied warranty of
  10. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  11. Affero General Public License for more details.
  12. You should have received a copy of the GNU Affero General Public License
  13. along with this program. If not, see <http://www.gnu.org/licenses/>.
  14. SPDX-License-Identifier: AGPL3.0-or-later
  15. */
  16. /**
  17. * @file gnunet-namecache.c
  18. * @brief command line tool to inspect the name cache
  19. * @author Christian Grothoff
  20. *
  21. * TODO:
  22. * - test
  23. */
  24. #include "platform.h"
  25. #include "gnunet_util_lib.h"
  26. #include "gnunet_dnsparser_lib.h"
  27. #include "gnunet_identity_service.h"
  28. #include "gnunet_gnsrecord_lib.h"
  29. #include "gnunet_namecache_service.h"
  30. /**
  31. * Handle to the namecache.
  32. */
  33. static struct GNUNET_NAMECACHE_Handle *ns;
  34. /**
  35. * Queue entry for the 'query' operation.
  36. */
  37. static struct GNUNET_NAMECACHE_QueueEntry *qe;
  38. /**
  39. * Name (label) of the records to list.
  40. */
  41. static char *name;
  42. /**
  43. * Public key of the zone to look in.
  44. */
  45. static struct GNUNET_CRYPTO_EcdsaPublicKey pubkey;
  46. /**
  47. * Public key of the zone to look in, in ASCII.
  48. */
  49. static char *pkey;
  50. /**
  51. * Global return value
  52. */
  53. static int ret;
  54. /**
  55. * Task run on shutdown. Cleans up everything.
  56. *
  57. * @param cls unused
  58. */
  59. static void
  60. do_shutdown (void *cls)
  61. {
  62. if (NULL != qe)
  63. {
  64. GNUNET_NAMECACHE_cancel (qe);
  65. qe = NULL;
  66. }
  67. if (NULL != ns)
  68. {
  69. GNUNET_NAMECACHE_disconnect (ns);
  70. ns = NULL;
  71. }
  72. }
  73. /**
  74. * Process a record that was stored in the namecache in a block.
  75. *
  76. * @param cls closure, NULL
  77. * @param rd_len number of entries in @a rd array
  78. * @param rd array of records with data to store
  79. */
  80. static void
  81. display_records_from_block (void *cls,
  82. unsigned int rd_len,
  83. const struct GNUNET_GNSRECORD_Data *rd)
  84. {
  85. const char *typestring;
  86. char *s;
  87. unsigned int i;
  88. if (0 == rd_len)
  89. {
  90. fprintf (stdout, _ ("No records found for `%s'"), name);
  91. return;
  92. }
  93. fprintf (stdout, "%s:\n", name);
  94. for (i = 0; i < rd_len; i++)
  95. {
  96. typestring = GNUNET_GNSRECORD_number_to_typename (rd[i].record_type);
  97. s = GNUNET_GNSRECORD_value_to_string (rd[i].record_type,
  98. rd[i].data,
  99. rd[i].data_size);
  100. if (NULL == s)
  101. {
  102. fprintf (stdout,
  103. _ ("\tCorrupt or unsupported record of type %u\n"),
  104. (unsigned int) rd[i].record_type);
  105. continue;
  106. }
  107. fprintf (stdout, "\t%s: %s\n", typestring, s);
  108. GNUNET_free (s);
  109. }
  110. fprintf (stdout, "%s", "\n");
  111. }
  112. /**
  113. * Display block obtained from listing (by name).
  114. *
  115. * @param cls NULL
  116. * @param block NULL if not found
  117. */
  118. static void
  119. handle_block (void *cls, const struct GNUNET_GNSRECORD_Block *block)
  120. {
  121. qe = NULL;
  122. if (NULL == block)
  123. {
  124. fprintf (stderr, "No matching block found\n");
  125. }
  126. else if (GNUNET_OK !=
  127. GNUNET_GNSRECORD_block_decrypt (block,
  128. &pubkey,
  129. name,
  130. &display_records_from_block,
  131. NULL))
  132. {
  133. fprintf (stderr, "Failed to decrypt block!\n");
  134. }
  135. GNUNET_SCHEDULER_shutdown ();
  136. }
  137. /**
  138. * Main function that will be run.
  139. *
  140. * @param cls closure
  141. * @param args remaining command-line arguments
  142. * @param cfgfile name of the configuration file used (for saving, can be NULL!)
  143. * @param cfg configuration
  144. */
  145. static void
  146. run (void *cls,
  147. char *const *args,
  148. const char *cfgfile,
  149. const struct GNUNET_CONFIGURATION_Handle *cfg)
  150. {
  151. struct GNUNET_HashCode dhash;
  152. if (NULL == pkey)
  153. {
  154. fprintf (stderr, _ ("You must specify which zone should be accessed\n"));
  155. return;
  156. }
  157. if (GNUNET_OK !=
  158. GNUNET_CRYPTO_ecdsa_public_key_from_string (pkey, strlen (pkey), &pubkey))
  159. {
  160. fprintf (stderr, _ ("Invalid public key for zone `%s'\n"), pkey);
  161. GNUNET_SCHEDULER_shutdown ();
  162. return;
  163. }
  164. if (NULL == name)
  165. {
  166. fprintf (stderr, _ ("You must specify a name\n"));
  167. return;
  168. }
  169. GNUNET_SCHEDULER_add_shutdown (&do_shutdown, NULL);
  170. ns = GNUNET_NAMECACHE_connect (cfg);
  171. GNUNET_GNSRECORD_query_from_public_key (&pubkey, name, &dhash);
  172. qe = GNUNET_NAMECACHE_lookup_block (ns, &dhash, &handle_block, NULL);
  173. }
  174. /**
  175. * The main function for gnunet-namecache.
  176. *
  177. * @param argc number of arguments from the command line
  178. * @param argv command line arguments
  179. * @return 0 ok, 1 on error
  180. */
  181. int
  182. main (int argc, char *const *argv)
  183. {
  184. struct GNUNET_GETOPT_CommandLineOption options[] =
  185. { GNUNET_GETOPT_option_string ('n',
  186. "name",
  187. "NAME",
  188. gettext_noop (
  189. "name of the record to add/delete/display"),
  190. &name),
  191. GNUNET_GETOPT_option_string (
  192. 'z',
  193. "zone",
  194. "PKEY",
  195. gettext_noop ("specifies the public key of the zone to look in"),
  196. &pkey),
  197. GNUNET_GETOPT_OPTION_END };
  198. if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv))
  199. return 2;
  200. GNUNET_log_setup ("gnunet-namecache", "WARNING", NULL);
  201. if (GNUNET_OK != GNUNET_PROGRAM_run (argc,
  202. argv,
  203. "gnunet-namecache",
  204. _ ("GNUnet zone manipulation tool"),
  205. options,
  206. &run,
  207. NULL))
  208. {
  209. GNUNET_free ((void *) argv);
  210. return 1;
  211. }
  212. GNUNET_free ((void *) argv);
  213. return ret;
  214. }
  215. /* end of gnunet-namecache.c */