diff options
author | Christian Grothoff <christian@grothoff.org> | 2022-11-21 15:09:10 +0100 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2022-11-21 15:09:10 +0100 |
commit | 92c6328195c3bed9abbd56625fcab5952869289c (patch) | |
tree | baecbe996589f4fdc652636e11f078bba94776ae | |
parent | ee778d9e8963b4daaae7fbd0eecab7a124c7e1d0 (diff) | |
parent | bdab06894ca42106651e7328657cf87c779b6acf (diff) | |
download | gnunet-92c6328195c3bed9abbd56625fcab5952869289c.tar.gz gnunet-92c6328195c3bed9abbd56625fcab5952869289c.zip |
Merge branch 'master' of git+ssh://git.gnunet.org/gnunet
-rw-r--r-- | doc/man/gnunet-namestore.1 | 88 | ||||
-rw-r--r-- | src/namestore/Makefile.am | 1 | ||||
-rw-r--r-- | src/namestore/gnunet-namestore.c | 878 | ||||
-rwxr-xr-x[-rw-r--r--] | src/namestore/test_namestore_put_multiple.sh | 49 | ||||
-rwxr-xr-x | src/namestore/test_namestore_put_stdin.sh | 68 |
5 files changed, 669 insertions, 415 deletions
diff --git a/doc/man/gnunet-namestore.1 b/doc/man/gnunet-namestore.1 index 9391e21bb..6915aed6e 100644 --- a/doc/man/gnunet-namestore.1 +++ b/doc/man/gnunet-namestore.1 | |||
@@ -43,9 +43,8 @@ | |||
43 | .Op Fl o | -omit-private | 43 | .Op Fl o | -omit-private |
44 | .Op Fl P | -purge-orphans | 44 | .Op Fl P | -purge-orphans |
45 | .Op Fl p | -public | 45 | .Op Fl p | -public |
46 | .Op Fl r Ar PKEY | Fl -reverse= Ns Ar PKEY | ||
47 | .Op Fl R Ar RECORDLINE | Fl -replace= Ns Ar RECORDLINE | ||
48 | .Op Fl s | -shadow | 46 | .Op Fl s | -shadow |
47 | .Op Fl S | -from-stdin | ||
49 | .Op Fl T | -include-maintenance | 48 | .Op Fl T | -include-maintenance |
50 | .Op Fl t Ar TYPE | Fl -type= Ns Ar TYPE | 49 | .Op Fl t Ar TYPE | Fl -type= Ns Ar TYPE |
51 | .Op Fl u Ar URI | Fl -uri= Ns Ar URI | 50 | .Op Fl u Ar URI | Fl -uri= Ns Ar URI |
@@ -53,6 +52,7 @@ | |||
53 | .Op Fl V Ar VALUE | Fl -value= Ns Ar VALUE | 52 | .Op Fl V Ar VALUE | Fl -value= Ns Ar VALUE |
54 | .Op Fl X | -purge-zone-records | 53 | .Op Fl X | -purge-zone-records |
55 | .Op Fl z Ar EGO | Fl -zone= Ns Ar EGO | 54 | .Op Fl z Ar EGO | Fl -zone= Ns Ar EGO |
55 | .Op Fl Z Ar KEY | Fl -zone-to-name= Ns Ar KEY | ||
56 | .Sh DESCRIPTION | 56 | .Sh DESCRIPTION |
57 | .Nm | 57 | .Nm |
58 | can be used to manipulate records in a GNS zone. | 58 | can be used to manipulate records in a GNS zone. |
@@ -102,23 +102,42 @@ Delete orphaned records from namestore. | |||
102 | .It Fl p | -public | 102 | .It Fl p | -public |
103 | Create a record that is public (shared with other users that know the | 103 | Create a record that is public (shared with other users that know the |
104 | label). | 104 | label). |
105 | .It Fl r Ar PKEY | Fl -reverse= Ns Ar PKEY | 105 | .It Fl r | -recordline |
106 | Determine our GNS name for the given public key (reverse lookup of the | 106 | Changes the output format of zones and records to recordline. |
107 | PKEY) in the given zone. | ||
108 | .It Fl R Ar RECORDLINE | Fl -replace= Ns Ar RECORDLINE | ||
109 | Sets record set to values given in RECORDLINE. | ||
110 | This option can be specified multiple times to provide multiple | ||
111 | records for the record set. | ||
112 | Existing records under the same label will be deleted. | ||
113 | The format for the RECORDLINE is "TTL TYPE FLAGS VALUE" where TTL is | ||
114 | the time to live in seconds (unit must not be given explicitly, | ||
115 | seconds is always implied), TYPE is the DNS/GNS record type, | ||
116 | FLAGS is "(N)ORMAL", "(S)HADOW" or "(P)UBLIC". | ||
117 | The VALUE follows the usual human-readable value format(s) of DNS/GNS. | ||
118 | .It Fl s | -shadow | 107 | .It Fl s | -shadow |
119 | Create a record that is a shadow record. | 108 | Create a record that is a shadow record. |
120 | Shadow records are only used once all other records of the same type | 109 | Shadow records are only used once all other records of the same type |
121 | under the same label have expired. | 110 | under the same label have expired. |
111 | .It Fl S | -from-stdin | ||
112 | Read recordlines from stdin until EOF is encountered. | ||
113 | The format uses | ||
114 | .B recordlines | ||
115 | : | ||
116 | A record in a recordline follows the format | ||
117 | |||
118 | NAME.EGO: | ||
119 | TYPE EXPIRATION [FLAGS] VALUE | ||
120 | ... | ||
121 | Multiple records may be provided for a name. | ||
122 | |||
123 | EXPIRATION is given in microseconds without a unit (e.g. 3600000000 for 3600 seconds). | ||
124 | |||
125 | FLAGS is a concatenation of record flags. | ||
126 | Possible values for flags and their meaning are: | ||
127 | .Pp | ||
128 | p: Public | ||
129 | s: Shadow | ||
130 | S: Supplemental | ||
131 | C: Critical | ||
132 | r: Relative expiration | ||
133 | |||
134 | TYPE and VALUE are used in the same way as for the "-t" and "-V" options. | ||
135 | Example formats for recordlines can be output using the "-D" flag combined | ||
136 | with "--recordline". | ||
137 | An example record set in recordline format can be found in the examples. | ||
138 | It is possible to specify multiple record sets. | ||
139 | Can only be used in combination with "-a" to add the parsed record sets. | ||
140 | Existing record sets under names will be replaced. | ||
122 | .It Fl T | -include-maintenance | 141 | .It Fl T | -include-maintenance |
123 | Show maintenance records such as TOMBSTONEs. Use in combination with --display. | 142 | Show maintenance records such as TOMBSTONEs. Use in combination with --display. |
124 | .It Fl t Ar TYPE | Fl -type= Ns Ar TYPE | 143 | .It Fl t Ar TYPE | Fl -type= Ns Ar TYPE |
@@ -144,8 +163,45 @@ Base32-encoding using the GNUNET_NAMESTORE_EGO_PRIVATE_KEY environment | |||
144 | variable. The latter is useful to improve performance of tools like | 163 | variable. The latter is useful to improve performance of tools like |
145 | Ascension as it allows the command to skip IPC with the identity | 164 | Ascension as it allows the command to skip IPC with the identity |
146 | management subsystem. | 165 | management subsystem. |
166 | .It Fl Z Ar KEY | Fl -zone-to-name= Ns Ar KEY | ||
167 | Determine our GNS name for the given public key (reverse lookup of the | ||
168 | KEY) in the given zone. | ||
147 | .El | 169 | .El |
148 | .\".Sh EXAMPLES | 170 | .Sh EXAMPLES |
171 | .Tp | ||
172 | .Nm | ||
173 | -z example -a -n www -t A -V "1.2.3.4" -e 1d -p | ||
174 | .Tp | ||
175 | .Pp | ||
176 | .Dl Add a public record for ego "example" with name "www" containing an IP address. | ||
177 | .sp | ||
178 | .Tp | ||
179 | .Nm | ||
180 | -z example -D | ||
181 | .Tp | ||
182 | .Pp | ||
183 | .Dl Show all records for ego "example". | ||
184 | .sp | ||
185 | .Tp | ||
186 | .Nm | ||
187 | -z example -D -r | ||
188 | .Tp | ||
189 | .Pp | ||
190 | .Dl Show all records for ego "example" in recordline format. | ||
191 | .sp | ||
192 | .Tp | ||
193 | .Nm | ||
194 | --add --from-stdin <<EOF | ||
195 | www.alice: | ||
196 | A 3600000000 [pr] 1.2.3.4 | ||
197 | TXT 3600000001 [pr] Hello World | ||
198 | |||
199 | www.bob: | ||
200 | A 12345679000000 [pr] 4.3.2.1 | ||
201 | EOF | ||
202 | .Tp | ||
203 | .Pp | ||
204 | .Dl Read record sets in recordline format from stdin. | ||
149 | .\".Sh FILES | 205 | .\".Sh FILES |
150 | .Sh SEE ALSO | 206 | .Sh SEE ALSO |
151 | .Xr gnunet-gns 1 , | 207 | .Xr gnunet-gns 1 , |
diff --git a/src/namestore/Makefile.am b/src/namestore/Makefile.am index fb2a670bc..a0ca32fa4 100644 --- a/src/namestore/Makefile.am +++ b/src/namestore/Makefile.am | |||
@@ -514,6 +514,7 @@ test_plugin_namestore_postgres_LDADD = \ | |||
514 | 514 | ||
515 | check_SCRIPTS = \ | 515 | check_SCRIPTS = \ |
516 | test_namestore_put.sh \ | 516 | test_namestore_put.sh \ |
517 | test_namestore_put_stdin.sh \ | ||
517 | test_namestore_lookup.sh \ | 518 | test_namestore_lookup.sh \ |
518 | test_namestore_delete.sh \ | 519 | test_namestore_delete.sh \ |
519 | test_namestore_zonefile_import.sh | 520 | test_namestore_zonefile_import.sh |
diff --git a/src/namestore/gnunet-namestore.c b/src/namestore/gnunet-namestore.c index 36a0a9ba3..207394dd9 100644 --- a/src/namestore/gnunet-namestore.c +++ b/src/namestore/gnunet-namestore.c | |||
@@ -32,6 +32,7 @@ | |||
32 | #include <gnunet_gnsrecord_lib.h> | 32 | #include <gnunet_gnsrecord_lib.h> |
33 | #include <gnunet_gns_service.h> | 33 | #include <gnunet_gns_service.h> |
34 | #include <gnunet_namestore_service.h> | 34 | #include <gnunet_namestore_service.h> |
35 | #include <inttypes.h> | ||
35 | 36 | ||
36 | /** | 37 | /** |
37 | * The upper bound for the zone iteration interval | 38 | * The upper bound for the zone iteration interval |
@@ -119,11 +120,6 @@ static struct GNUNET_NAMESTORE_Handle *ns; | |||
119 | static struct GNUNET_IDENTITY_PrivateKey zone_pkey; | 120 | static struct GNUNET_IDENTITY_PrivateKey zone_pkey; |
120 | 121 | ||
121 | /** | 122 | /** |
122 | * Handle to identity lookup. | ||
123 | */ | ||
124 | static struct GNUNET_IDENTITY_EgoLookup *el; | ||
125 | |||
126 | /** | ||
127 | * Identity service handle | 123 | * Identity service handle |
128 | */ | 124 | */ |
129 | static struct GNUNET_IDENTITY_Handle *idh; | 125 | static struct GNUNET_IDENTITY_Handle *idh; |
@@ -134,11 +130,6 @@ static struct GNUNET_IDENTITY_Handle *idh; | |||
134 | static char *ego_name; | 130 | static char *ego_name; |
135 | 131 | ||
136 | /** | 132 | /** |
137 | * Desired action is to add a record. | ||
138 | */ | ||
139 | static int add; | ||
140 | |||
141 | /** | ||
142 | * Queue entry for the 'add-uri' operation. | 133 | * Queue entry for the 'add-uri' operation. |
143 | */ | 134 | */ |
144 | static struct GNUNET_NAMESTORE_QueueEntry *add_qe_uri; | 135 | static struct GNUNET_NAMESTORE_QueueEntry *add_qe_uri; |
@@ -168,6 +159,10 @@ static struct MarkedRecord *marked_head; | |||
168 | */ | 159 | */ |
169 | static struct MarkedRecord *marked_tail; | 160 | static struct MarkedRecord *marked_tail; |
170 | 161 | ||
162 | /** | ||
163 | * Configuration handle | ||
164 | */ | ||
165 | const struct GNUNET_CONFIGURATION_Handle *cfg; | ||
171 | 166 | ||
172 | /** | 167 | /** |
173 | * Ego list | 168 | * Ego list |
@@ -180,14 +175,24 @@ static struct EgoEntry *ego_head; | |||
180 | static struct EgoEntry *ego_tail; | 175 | static struct EgoEntry *ego_tail; |
181 | 176 | ||
182 | /** | 177 | /** |
178 | * List iterator for the 'list' operation. | ||
179 | */ | ||
180 | static struct GNUNET_NAMESTORE_ZoneIterator *list_it; | ||
181 | |||
182 | /** | ||
183 | * Run in read from stdin mode. | ||
184 | */ | ||
185 | static int read_from_stdin; | ||
186 | |||
187 | /** | ||
183 | * Desired action is to list records. | 188 | * Desired action is to list records. |
184 | */ | 189 | */ |
185 | static int list; | 190 | static int list; |
186 | 191 | ||
187 | /** | 192 | /** |
188 | * List iterator for the 'list' operation. | 193 | * Desired action is to add a record. |
189 | */ | 194 | */ |
190 | static struct GNUNET_NAMESTORE_ZoneIterator *list_it; | 195 | static int add; |
191 | 196 | ||
192 | /** | 197 | /** |
193 | * Desired action is to remove a record. | 198 | * Desired action is to remove a record. |
@@ -210,6 +215,12 @@ static int is_shadow; | |||
210 | static int omit_private; | 215 | static int omit_private; |
211 | 216 | ||
212 | /** | 217 | /** |
218 | * Output in recordline format | ||
219 | */ | ||
220 | static int output_recordline; | ||
221 | |||
222 | |||
223 | /** | ||
213 | * Purge zone contents | 224 | * Purge zone contents |
214 | */ | 225 | */ |
215 | static int purge_zone; | 226 | static int purge_zone; |
@@ -240,6 +251,11 @@ static struct GNUNET_NAMESTORE_QueueEntry *del_qe; | |||
240 | static struct GNUNET_NAMESTORE_QueueEntry *set_qe; | 251 | static struct GNUNET_NAMESTORE_QueueEntry *set_qe; |
241 | 252 | ||
242 | /** | 253 | /** |
254 | * Queue entry for begin/commit | ||
255 | */ | ||
256 | static struct GNUNET_NAMESTORE_QueueEntry *ns_qe; | ||
257 | |||
258 | /** | ||
243 | * Name of the records to add/list/remove. | 259 | * Name of the records to add/list/remove. |
244 | */ | 260 | */ |
245 | static char *name; | 261 | static char *name; |
@@ -325,37 +341,193 @@ static struct RecordSetEntry *recordset; | |||
325 | static struct GNUNET_SCHEDULER_Task *purge_task; | 341 | static struct GNUNET_SCHEDULER_Task *purge_task; |
326 | 342 | ||
327 | /** | 343 | /** |
328 | * Task run on shutdown. Cleans up everything. | 344 | * Parse expiration time. |
329 | * | 345 | * |
330 | * @param cls unused | 346 | * @param expirationstring text to parse |
347 | * @param[out] etime_is_rel set to #GNUNET_YES if time is relative | ||
348 | * @param[out] etime set to expiration time (abs or rel) | ||
349 | * @return #GNUNET_OK on success | ||
331 | */ | 350 | */ |
351 | static int | ||
352 | parse_expiration (const char *expirationstring, | ||
353 | int *etime_is_rel, | ||
354 | uint64_t *etime) | ||
355 | { | ||
356 | struct GNUNET_TIME_Relative etime_rel; | ||
357 | struct GNUNET_TIME_Absolute etime_abs; | ||
358 | |||
359 | if (0 == strcmp (expirationstring, "never")) | ||
360 | { | ||
361 | *etime = GNUNET_TIME_UNIT_FOREVER_ABS.abs_value_us; | ||
362 | *etime_is_rel = GNUNET_NO; | ||
363 | return GNUNET_OK; | ||
364 | } | ||
365 | if (GNUNET_OK == | ||
366 | GNUNET_STRINGS_fancy_time_to_relative (expirationstring, &etime_rel)) | ||
367 | { | ||
368 | *etime_is_rel = GNUNET_YES; | ||
369 | *etime = etime_rel.rel_value_us; | ||
370 | if (GNUNET_TIME_relative_cmp (etime_rel, <, WARN_RELATIVE_EXPIRATION_LIMIT)) | ||
371 | { | ||
372 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
373 | "Relative expiration times of less than %s are not recommended. To improve availability, consider increasing this value.\n", | ||
374 | GNUNET_STRINGS_relative_time_to_string ( | ||
375 | WARN_RELATIVE_EXPIRATION_LIMIT, GNUNET_NO)); | ||
376 | } | ||
377 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
378 | "Storing record with relative expiration time of %s\n", | ||
379 | GNUNET_STRINGS_relative_time_to_string (etime_rel, GNUNET_NO)); | ||
380 | return GNUNET_OK; | ||
381 | } | ||
382 | if (GNUNET_OK == | ||
383 | GNUNET_STRINGS_fancy_time_to_absolute (expirationstring, &etime_abs)) | ||
384 | { | ||
385 | *etime_is_rel = GNUNET_NO; | ||
386 | *etime = etime_abs.abs_value_us; | ||
387 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
388 | "Storing record with absolute expiration time of %s\n", | ||
389 | GNUNET_STRINGS_absolute_time_to_string (etime_abs)); | ||
390 | return GNUNET_OK; | ||
391 | } | ||
392 | return GNUNET_SYSERR; | ||
393 | } | ||
394 | |||
395 | |||
396 | static int | ||
397 | parse_recordline (const char *line) | ||
398 | { | ||
399 | struct RecordSetEntry **head = &recordset; | ||
400 | struct RecordSetEntry *r; | ||
401 | struct GNUNET_GNSRECORD_Data record; | ||
402 | char *cp; | ||
403 | char *tok; | ||
404 | char *saveptr; | ||
405 | void *raw_data; | ||
406 | |||
407 | cp = GNUNET_strdup (line); | ||
408 | tok = strtok_r (cp, " ", &saveptr); | ||
409 | if (NULL == tok) | ||
410 | { | ||
411 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
412 | _ ("Missing entries in record line `%s'.\n"), | ||
413 | line); | ||
414 | GNUNET_free (cp); | ||
415 | return GNUNET_SYSERR; | ||
416 | } | ||
417 | record.record_type = GNUNET_GNSRECORD_typename_to_number (tok); | ||
418 | if (UINT32_MAX == record.record_type) | ||
419 | { | ||
420 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _ ("Unknown record type `%s'\n"), tok); | ||
421 | GNUNET_free (cp); | ||
422 | return GNUNET_SYSERR; | ||
423 | } | ||
424 | tok = strtok_r (NULL, " ", &saveptr); | ||
425 | if (NULL == tok) | ||
426 | { | ||
427 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
428 | _ ("Empty record line argument is not allowed.\n")); | ||
429 | GNUNET_free (cp); | ||
430 | return GNUNET_SYSERR; | ||
431 | } | ||
432 | if (1 != sscanf (tok, "%" SCNu64, &record.expiration_time)) | ||
433 | { | ||
434 | fprintf (stderr, | ||
435 | _ ("Error parsing expiration time %s.\n"), tok); | ||
436 | GNUNET_free (cp); | ||
437 | return GNUNET_SYSERR; | ||
438 | } | ||
439 | tok = strtok_r (NULL, " ", &saveptr); | ||
440 | if (NULL == tok) | ||
441 | { | ||
442 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
443 | _ ("Empty record line argument is not allowed.\n")); | ||
444 | GNUNET_free (cp); | ||
445 | return GNUNET_SYSERR; | ||
446 | } | ||
447 | record.flags = GNUNET_GNSRECORD_RF_NONE; | ||
448 | if (NULL != strchr (tok, (unsigned char) 'r')) | ||
449 | record.flags |= GNUNET_GNSRECORD_RF_RELATIVE_EXPIRATION; | ||
450 | if (NULL == strchr (tok, (unsigned char) 'p')) /* p = public */ | ||
451 | record.flags |= GNUNET_GNSRECORD_RF_PRIVATE; | ||
452 | if (NULL != strchr (tok, (unsigned char) 'S')) | ||
453 | record.flags |= GNUNET_GNSRECORD_RF_SUPPLEMENTAL; | ||
454 | if (NULL != strchr (tok, (unsigned char) 's')) | ||
455 | record.flags |= GNUNET_GNSRECORD_RF_SHADOW; | ||
456 | if (NULL != strchr (tok, (unsigned char) 'C')) | ||
457 | record.flags |= GNUNET_GNSRECORD_RF_CRITICAL; | ||
458 | tok = strtok_r (NULL, " ", &saveptr); | ||
459 | if (NULL == tok) | ||
460 | { | ||
461 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
462 | _ ("Empty record line argument is not allowed.\n")); | ||
463 | GNUNET_free (cp); | ||
464 | return GNUNET_SYSERR; | ||
465 | } | ||
466 | if (GNUNET_OK != GNUNET_GNSRECORD_string_to_value (record.record_type, | ||
467 | tok, | ||
468 | &raw_data, | ||
469 | &record.data_size)) | ||
470 | { | ||
471 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
472 | _ ("Invalid record data for type %s: `%s'.\n"), | ||
473 | GNUNET_GNSRECORD_number_to_typename (record.record_type), | ||
474 | tok); | ||
475 | return GNUNET_SYSERR; | ||
476 | } | ||
477 | |||
478 | r = GNUNET_malloc (sizeof(struct RecordSetEntry) + record.data_size); | ||
479 | r->next = *head; | ||
480 | record.data = &r[1]; | ||
481 | memcpy (&r[1], raw_data, record.data_size); | ||
482 | GNUNET_free (raw_data); | ||
483 | r->record = record; | ||
484 | *head = r; | ||
485 | return GNUNET_OK; | ||
486 | } | ||
487 | |||
332 | static void | 488 | static void |
333 | do_shutdown (void *cls) | 489 | reset_handles (void) |
334 | { | 490 | { |
335 | struct EgoEntry *ego_entry; | ||
336 | struct EgoEntry *ego_tmp; | ||
337 | struct MarkedRecord *mrec; | 491 | struct MarkedRecord *mrec; |
338 | struct MarkedRecord *mrec_tmp; | 492 | struct MarkedRecord *mrec_tmp; |
339 | (void) cls; | 493 | struct RecordSetEntry *rs_entry; |
494 | |||
495 | rs_entry = recordset; | ||
496 | while (NULL != (rs_entry = recordset)) | ||
497 | { | ||
498 | recordset = recordset->next; | ||
499 | GNUNET_free (rs_entry); | ||
500 | } | ||
501 | recordset = NULL; | ||
340 | if (NULL != ego_name) | 502 | if (NULL != ego_name) |
341 | { | 503 | { |
342 | GNUNET_free (ego_name); | 504 | GNUNET_free (ego_name); |
343 | ego_name = NULL; | 505 | ego_name = NULL; |
344 | } | 506 | } |
345 | if (NULL != purge_task) | 507 | if (NULL != name) |
346 | { | 508 | { |
347 | GNUNET_SCHEDULER_cancel (purge_task); | 509 | GNUNET_free (name); |
348 | purge_task = NULL; | 510 | name = NULL; |
349 | } | 511 | } |
350 | if (NULL != idh) | 512 | if (NULL != value) |
351 | { | 513 | { |
352 | GNUNET_IDENTITY_disconnect (idh); | 514 | GNUNET_free (value); |
353 | idh = NULL; | 515 | value = NULL; |
516 | } | ||
517 | if (NULL != uri) | ||
518 | { | ||
519 | GNUNET_free (uri); | ||
520 | uri = NULL; | ||
354 | } | 521 | } |
355 | if (NULL != el) | 522 | if (NULL != expirationstring) |
356 | { | 523 | { |
357 | GNUNET_IDENTITY_ego_lookup_cancel (el); | 524 | GNUNET_free (expirationstring); |
358 | el = NULL; | 525 | expirationstring = NULL; |
526 | } | ||
527 | if (NULL != purge_task) | ||
528 | { | ||
529 | GNUNET_SCHEDULER_cancel (purge_task); | ||
530 | purge_task = NULL; | ||
359 | } | 531 | } |
360 | for (mrec = marked_head; NULL != mrec;) | 532 | for (mrec = marked_head; NULL != mrec;) |
361 | { | 533 | { |
@@ -364,13 +536,6 @@ do_shutdown (void *cls) | |||
364 | GNUNET_free (mrec_tmp->name); | 536 | GNUNET_free (mrec_tmp->name); |
365 | GNUNET_free (mrec_tmp); | 537 | GNUNET_free (mrec_tmp); |
366 | } | 538 | } |
367 | for (ego_entry = ego_head; NULL != ego_entry;) | ||
368 | { | ||
369 | ego_tmp = ego_entry; | ||
370 | ego_entry = ego_entry->next; | ||
371 | GNUNET_free (ego_tmp->identifier); | ||
372 | GNUNET_free (ego_tmp); | ||
373 | } | ||
374 | if (NULL != list_it) | 539 | if (NULL != list_it) |
375 | { | 540 | { |
376 | GNUNET_NAMESTORE_zone_iteration_stop (list_it); | 541 | GNUNET_NAMESTORE_zone_iteration_stop (list_it); |
@@ -401,17 +566,12 @@ do_shutdown (void *cls) | |||
401 | GNUNET_NAMESTORE_cancel (del_qe); | 566 | GNUNET_NAMESTORE_cancel (del_qe); |
402 | del_qe = NULL; | 567 | del_qe = NULL; |
403 | } | 568 | } |
404 | if (NULL != ns) | 569 | if (NULL != reverse_qe) |
405 | { | 570 | { |
406 | GNUNET_NAMESTORE_disconnect (ns); | 571 | GNUNET_NAMESTORE_cancel (reverse_qe); |
407 | ns = NULL; | 572 | reverse_qe = NULL; |
408 | } | 573 | } |
409 | memset (&zone_pkey, 0, sizeof(zone_pkey)); | 574 | memset (&zone_pkey, 0, sizeof(zone_pkey)); |
410 | if (NULL != uri) | ||
411 | { | ||
412 | GNUNET_free (uri); | ||
413 | uri = NULL; | ||
414 | } | ||
415 | if (NULL != zm) | 575 | if (NULL != zm) |
416 | { | 576 | { |
417 | GNUNET_NAMESTORE_zone_monitor_stop (zm); | 577 | GNUNET_NAMESTORE_zone_monitor_stop (zm); |
@@ -422,18 +582,83 @@ do_shutdown (void *cls) | |||
422 | GNUNET_free (data); | 582 | GNUNET_free (data); |
423 | data = NULL; | 583 | data = NULL; |
424 | } | 584 | } |
585 | if (NULL != typestring) | ||
586 | { | ||
587 | GNUNET_free (typestring); | ||
588 | typestring = NULL; | ||
589 | } | ||
590 | list = 0; | ||
591 | is_public = 0; | ||
592 | is_shadow = 0; | ||
593 | purge_zone = 0; | ||
425 | } | 594 | } |
426 | 595 | ||
427 | 596 | ||
597 | |||
428 | /** | 598 | /** |
429 | * Check if we are finished, and if so, perform shutdown. | 599 | * Task run on shutdown. Cleans up everything. |
600 | * | ||
601 | * @param cls unused | ||
430 | */ | 602 | */ |
431 | static void | 603 | static void |
432 | test_finished () | 604 | do_shutdown (void *cls) |
433 | { | 605 | { |
434 | if ((NULL == add_qe) && (NULL == add_qe_uri) && (NULL == get_qe) && | 606 | struct EgoEntry *ego_entry; |
435 | (NULL == del_qe) && (NULL == reverse_qe) && (NULL == list_it)) | 607 | struct EgoEntry *ego_tmp; |
436 | GNUNET_SCHEDULER_shutdown (); | 608 | (void) cls; |
609 | |||
610 | reset_handles (); | ||
611 | if (NULL != ns_qe) | ||
612 | { | ||
613 | GNUNET_NAMESTORE_cancel (ns_qe); | ||
614 | ns_qe = NULL; | ||
615 | } | ||
616 | if (NULL != ns) | ||
617 | { | ||
618 | GNUNET_NAMESTORE_disconnect (ns); | ||
619 | ns = NULL; | ||
620 | } | ||
621 | if (NULL != idh) | ||
622 | { | ||
623 | GNUNET_IDENTITY_disconnect (idh); | ||
624 | idh = NULL; | ||
625 | } | ||
626 | for (ego_entry = ego_head; NULL != ego_entry;) | ||
627 | { | ||
628 | ego_tmp = ego_entry; | ||
629 | ego_entry = ego_entry->next; | ||
630 | GNUNET_free (ego_tmp->identifier); | ||
631 | GNUNET_free (ego_tmp); | ||
632 | } | ||
633 | } | ||
634 | |||
635 | static void | ||
636 | commit_cb (void *cls, enum GNUNET_ErrorCode ec) | ||
637 | { | ||
638 | ns_qe = NULL; | ||
639 | if (GNUNET_EC_NONE != ec) | ||
640 | { | ||
641 | fprintf (stderr, "Failed to commit to namestore: `%s'\n", | ||
642 | GNUNET_ErrorCode_get_hint (ec)); | ||
643 | ret = 1; | ||
644 | } | ||
645 | GNUNET_SCHEDULER_shutdown (); | ||
646 | } | ||
647 | |||
648 | static void | ||
649 | process_command_stdin (); | ||
650 | |||
651 | |||
652 | static void | ||
653 | finish_command (void) | ||
654 | { | ||
655 | reset_handles (); | ||
656 | if (read_from_stdin) | ||
657 | { | ||
658 | process_command_stdin (); | ||
659 | return; | ||
660 | } | ||
661 | ns_qe = GNUNET_NAMESTORE_transaction_commit (ns, &commit_cb, NULL); | ||
437 | } | 662 | } |
438 | 663 | ||
439 | 664 | ||
@@ -452,7 +677,7 @@ add_continuation (void *cls, enum GNUNET_ErrorCode ec) | |||
452 | ret = 1; | 677 | ret = 1; |
453 | } | 678 | } |
454 | ret = 0; | 679 | ret = 0; |
455 | test_finished (); | 680 | finish_command (); |
456 | } | 681 | } |
457 | 682 | ||
458 | 683 | ||
@@ -467,7 +692,7 @@ del_continuation (void *cls, enum GNUNET_ErrorCode ec) | |||
467 | _ ("Deleting record failed: %s\n"), GNUNET_ErrorCode_get_hint ( | 692 | _ ("Deleting record failed: %s\n"), GNUNET_ErrorCode_get_hint ( |
468 | ec)); | 693 | ec)); |
469 | } | 694 | } |
470 | test_finished (); | 695 | finish_command (); |
471 | } | 696 | } |
472 | 697 | ||
473 | static void | 698 | static void |
@@ -496,7 +721,7 @@ purge_next_record (void *cls) | |||
496 | if (NULL == marked_head) | 721 | if (NULL == marked_head) |
497 | { | 722 | { |
498 | ret = 0; | 723 | ret = 0; |
499 | test_finished (); | 724 | finish_command (); |
500 | return; | 725 | return; |
501 | } | 726 | } |
502 | mrec = marked_head; | 727 | mrec = marked_head; |
@@ -527,7 +752,7 @@ zone_iteration_finished (void *cls) | |||
527 | return; | 752 | return; |
528 | } | 753 | } |
529 | ret = 0; | 754 | ret = 0; |
530 | test_finished (); | 755 | finish_command (); |
531 | } | 756 | } |
532 | 757 | ||
533 | 758 | ||
@@ -541,7 +766,7 @@ zone_iteration_error_cb (void *cls) | |||
541 | list_it = NULL; | 766 | list_it = NULL; |
542 | fprintf (stderr, "Error iterating over zone\n"); | 767 | fprintf (stderr, "Error iterating over zone\n"); |
543 | ret = 1; | 768 | ret = 1; |
544 | test_finished (); | 769 | finish_command (); |
545 | } | 770 | } |
546 | 771 | ||
547 | static void | 772 | static void |
@@ -681,18 +906,33 @@ display_record (const struct GNUNET_IDENTITY_PrivateKey *zone_key, | |||
681 | at.abs_value_us = rd[i].expiration_time; | 906 | at.abs_value_us = rd[i].expiration_time; |
682 | ets = GNUNET_STRINGS_absolute_time_to_string (at); | 907 | ets = GNUNET_STRINGS_absolute_time_to_string (at); |
683 | } | 908 | } |
684 | fprintf (stdout, | 909 | char flgstr[16]; |
685 | "\t%s: %s (%s)\t%s\t%s\n", | 910 | sprintf (flgstr, "[%s%s%s%s%s]", |
686 | typestr, | 911 | (rd[i].flags & GNUNET_GNSRECORD_RF_PRIVATE) ? "" : "p", |
687 | s, | 912 | (rd[i].flags & GNUNET_GNSRECORD_RF_SUPPLEMENTAL) ? "S" : "", |
688 | ets, | 913 | (rd[i].flags & GNUNET_GNSRECORD_RF_RELATIVE_EXPIRATION) ? "r" : "", |
689 | (0 != (rd[i].flags & GNUNET_GNSRECORD_RF_PRIVATE)) ? "PRIVATE" | 914 | (rd[i].flags & GNUNET_GNSRECORD_RF_SHADOW) ? "S" : "", |
915 | (rd[i].flags & GNUNET_GNSRECORD_RF_CRITICAL) ? "C" : ""); | ||
916 | if (output_recordline) | ||
917 | fprintf (stdout, | ||
918 | " %s %" PRIu64 " %s %s\n", | ||
919 | typestr, | ||
920 | rd[i].expiration_time, | ||
921 | flgstr, | ||
922 | s); | ||
923 | else | ||
924 | fprintf (stdout, | ||
925 | "\t%s: %s (%s)\t%s\t%s\n", | ||
926 | typestr, | ||
927 | s, | ||
928 | ets, | ||
929 | (0 != (rd[i].flags & GNUNET_GNSRECORD_RF_PRIVATE)) ? "PRIVATE" | ||
690 | : "PUBLIC", | 930 | : "PUBLIC", |
691 | (0 != (rd[i].flags & GNUNET_GNSRECORD_RF_SHADOW)) ? "SHADOW" | 931 | (0 != (rd[i].flags & GNUNET_GNSRECORD_RF_SHADOW)) ? "SHADOW" |
692 | : ""); | 932 | : ""); |
693 | GNUNET_free (s); | 933 | GNUNET_free (s); |
694 | } | 934 | } |
695 | fprintf (stdout, "%s", "\n"); | 935 | // fprintf (stdout, "%s", "\n"); |
696 | } | 936 | } |
697 | 937 | ||
698 | static void | 938 | static void |
@@ -797,7 +1037,7 @@ display_record_lookup (void *cls, | |||
797 | (void) zone_key; | 1037 | (void) zone_key; |
798 | get_qe = NULL; | 1038 | get_qe = NULL; |
799 | display_record (zone_key, rname, rd_len, rd); | 1039 | display_record (zone_key, rname, rd_len, rd); |
800 | test_finished (); | 1040 | finish_command (); |
801 | } | 1041 | } |
802 | 1042 | ||
803 | 1043 | ||
@@ -838,7 +1078,7 @@ lookup_error_cb (void *cls) | |||
838 | (void) cls; | 1078 | (void) cls; |
839 | get_qe = NULL; | 1079 | get_qe = NULL; |
840 | fprintf (stderr, "%s", "Failed to lookup record.\n"); | 1080 | fprintf (stderr, "%s", "Failed to lookup record.\n"); |
841 | test_finished (); | 1081 | finish_command (); |
842 | } | 1082 | } |
843 | 1083 | ||
844 | 1084 | ||
@@ -852,7 +1092,7 @@ add_error_cb (void *cls) | |||
852 | add_qe = NULL; | 1092 | add_qe = NULL; |
853 | GNUNET_break (0); | 1093 | GNUNET_break (0); |
854 | ret = 1; | 1094 | ret = 1; |
855 | test_finished (); | 1095 | finish_command (); |
856 | } | 1096 | } |
857 | 1097 | ||
858 | 1098 | ||
@@ -883,7 +1123,7 @@ get_existing_record (void *cls, | |||
883 | { | 1123 | { |
884 | GNUNET_break (0); | 1124 | GNUNET_break (0); |
885 | ret = 1; | 1125 | ret = 1; |
886 | test_finished (); | 1126 | finish_command (); |
887 | return; | 1127 | return; |
888 | } | 1128 | } |
889 | 1129 | ||
@@ -904,7 +1144,7 @@ get_existing_record (void *cls, | |||
904 | "A SOA record exists already under `%s', cannot add a second SOA to the same zone.\n"), | 1144 | "A SOA record exists already under `%s', cannot add a second SOA to the same zone.\n"), |
905 | rec_name); | 1145 | rec_name); |
906 | ret = 1; | 1146 | ret = 1; |
907 | test_finished (); | 1147 | finish_command (); |
908 | return; | 1148 | return; |
909 | } | 1149 | } |
910 | break; | 1150 | break; |
@@ -974,7 +1214,7 @@ handle_reverse_lookup (void *cls, | |||
974 | fprintf (stdout, "%s\n", reverse_pkey); | 1214 | fprintf (stdout, "%s\n", reverse_pkey); |
975 | else | 1215 | else |
976 | fprintf (stdout, "%s.%s\n", label, ego_name); | 1216 | fprintf (stdout, "%s.%s\n", label, ego_name); |
977 | test_finished (); | 1217 | finish_command (); |
978 | } | 1218 | } |
979 | 1219 | ||
980 | 1220 | ||
@@ -988,7 +1228,7 @@ del_lookup_error_cb (void *cls) | |||
988 | del_qe = NULL; | 1228 | del_qe = NULL; |
989 | GNUNET_break (0); | 1229 | GNUNET_break (0); |
990 | ret = 1; | 1230 | ret = 1; |
991 | test_finished (); | 1231 | finish_command (); |
992 | } | 1232 | } |
993 | 1233 | ||
994 | 1234 | ||
@@ -1025,7 +1265,7 @@ del_monitor (void *cls, | |||
1025 | "There are no records under label `%s' that could be deleted.\n"), | 1265 | "There are no records under label `%s' that could be deleted.\n"), |
1026 | label); | 1266 | label); |
1027 | ret = 1; | 1267 | ret = 1; |
1028 | test_finished (); | 1268 | finish_command (); |
1029 | return; | 1269 | return; |
1030 | } | 1270 | } |
1031 | if ((NULL == value) && (NULL == typestring)) | 1271 | if ((NULL == value) && (NULL == typestring)) |
@@ -1067,7 +1307,7 @@ del_monitor (void *cls, | |||
1067 | _ ( | 1307 | _ ( |
1068 | "There are no records under label `%s' that match the request for deletion.\n"), | 1308 | "There are no records under label `%s' that match the request for deletion.\n"), |
1069 | label); | 1309 | label); |
1070 | test_finished (); | 1310 | finish_command (); |
1071 | return; | 1311 | return; |
1072 | } | 1312 | } |
1073 | /* delete everything but what we copied to 'rdx' */ | 1313 | /* delete everything but what we copied to 'rdx' */ |
@@ -1081,59 +1321,6 @@ del_monitor (void *cls, | |||
1081 | } | 1321 | } |
1082 | 1322 | ||
1083 | 1323 | ||
1084 | /** | ||
1085 | * Parse expiration time. | ||
1086 | * | ||
1087 | * @param expirationstring text to parse | ||
1088 | * @param[out] etime_is_rel set to #GNUNET_YES if time is relative | ||
1089 | * @param[out] etime set to expiration time (abs or rel) | ||
1090 | * @return #GNUNET_OK on success | ||
1091 | */ | ||
1092 | static int | ||
1093 | parse_expiration (const char *expirationstring, | ||
1094 | int *etime_is_rel, | ||
1095 | uint64_t *etime) | ||
1096 | { | ||
1097 | struct GNUNET_TIME_Relative etime_rel; | ||
1098 | struct GNUNET_TIME_Absolute etime_abs; | ||
1099 | |||
1100 | if (0 == strcmp (expirationstring, "never")) | ||
1101 | { | ||
1102 | *etime = GNUNET_TIME_UNIT_FOREVER_ABS.abs_value_us; | ||
1103 | *etime_is_rel = GNUNET_NO; | ||
1104 | return GNUNET_OK; | ||
1105 | } | ||
1106 | if (GNUNET_OK == | ||
1107 | GNUNET_STRINGS_fancy_time_to_relative (expirationstring, &etime_rel)) | ||
1108 | { | ||
1109 | *etime_is_rel = GNUNET_YES; | ||
1110 | *etime = etime_rel.rel_value_us; | ||
1111 | if (GNUNET_TIME_relative_cmp (etime_rel, <, WARN_RELATIVE_EXPIRATION_LIMIT)) | ||
1112 | { | ||
1113 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
1114 | "Relative expiration times of less than %s are not recommended. To improve availability, consider increasing this value.\n", | ||
1115 | GNUNET_STRINGS_relative_time_to_string ( | ||
1116 | WARN_RELATIVE_EXPIRATION_LIMIT, GNUNET_NO)); | ||
1117 | } | ||
1118 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
1119 | "Storing record with relative expiration time of %s\n", | ||
1120 | GNUNET_STRINGS_relative_time_to_string (etime_rel, GNUNET_NO)); | ||
1121 | return GNUNET_OK; | ||
1122 | } | ||
1123 | if (GNUNET_OK == | ||
1124 | GNUNET_STRINGS_fancy_time_to_absolute (expirationstring, &etime_abs)) | ||
1125 | { | ||
1126 | *etime_is_rel = GNUNET_NO; | ||
1127 | *etime = etime_abs.abs_value_us; | ||
1128 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
1129 | "Storing record with absolute expiration time of %s\n", | ||
1130 | GNUNET_STRINGS_absolute_time_to_string (etime_abs)); | ||
1131 | return GNUNET_OK; | ||
1132 | } | ||
1133 | return GNUNET_SYSERR; | ||
1134 | } | ||
1135 | |||
1136 | |||
1137 | static void | 1324 | static void |
1138 | replace_cont (void *cls, enum GNUNET_ErrorCode ec) | 1325 | replace_cont (void *cls, enum GNUNET_ErrorCode ec) |
1139 | { | 1326 | { |
@@ -1147,7 +1334,7 @@ replace_cont (void *cls, enum GNUNET_ErrorCode ec) | |||
1147 | GNUNET_ErrorCode_get_hint (ec)); | 1334 | GNUNET_ErrorCode_get_hint (ec)); |
1148 | ret = 1; /* fail from 'main' */ | 1335 | ret = 1; /* fail from 'main' */ |
1149 | } | 1336 | } |
1150 | GNUNET_SCHEDULER_shutdown (); | 1337 | finish_command (); |
1151 | } | 1338 | } |
1152 | 1339 | ||
1153 | 1340 | ||
@@ -1173,14 +1360,7 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1173 | { | 1360 | { |
1174 | /* nothing more to be done */ | 1361 | /* nothing more to be done */ |
1175 | fprintf (stderr, _ ("No options given\n")); | 1362 | fprintf (stderr, _ ("No options given\n")); |
1176 | GNUNET_SCHEDULER_shutdown (); | 1363 | finish_command (); |
1177 | return; | ||
1178 | } | ||
1179 | ns = GNUNET_NAMESTORE_connect (cfg); | ||
1180 | if (NULL == ns) | ||
1181 | { | ||
1182 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
1183 | _ ("Failed to connect to namestore\n")); | ||
1184 | return; | 1364 | return; |
1185 | } | 1365 | } |
1186 | 1366 | ||
@@ -1190,24 +1370,23 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1190 | unsigned int rd_count; | 1370 | unsigned int rd_count; |
1191 | struct GNUNET_GNSRECORD_Data *rd; | 1371 | struct GNUNET_GNSRECORD_Data *rd; |
1192 | 1372 | ||
1193 | if (NULL == ego_name) | 1373 | /* FIXME: We could easily support append and delete with this as well */ |
1374 | if (! add) | ||
1194 | { | 1375 | { |
1195 | fprintf (stderr, | 1376 | fprintf (stderr, _ ("Recordlines only work with option `%s'\n"), |
1196 | _ ("Missing option `%s' for operation `%s'\n"), | 1377 | "-a"); |
1197 | "-z", | ||
1198 | _ ("replace")); | ||
1199 | GNUNET_SCHEDULER_shutdown (); | ||
1200 | ret = 1; | 1378 | ret = 1; |
1379 | finish_command (); | ||
1201 | return; | 1380 | return; |
1202 | } | 1381 | } |
1203 | if (NULL == name) | 1382 | if (NULL == name) |
1204 | { | 1383 | { |
1205 | fprintf (stderr, | 1384 | fprintf (stderr, |
1206 | _ ("Missing option `%s' for operation `%s'\n"), | 1385 | _ ("Missing option `%s' for operation `%s'\n"), |
1207 | "-R", | 1386 | "-n", |
1208 | _ ("replace")); | 1387 | _ ("name")); |
1209 | GNUNET_SCHEDULER_shutdown (); | ||
1210 | ret = 1; | 1388 | ret = 1; |
1389 | finish_command (); | ||
1211 | return; | 1390 | return; |
1212 | } | 1391 | } |
1213 | rd_count = 0; | 1392 | rd_count = 0; |
@@ -1235,8 +1414,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1235 | if (0 == strlen (nickstring)) | 1414 | if (0 == strlen (nickstring)) |
1236 | { | 1415 | { |
1237 | fprintf (stderr, _ ("Invalid nick `%s'\n"), nickstring); | 1416 | fprintf (stderr, _ ("Invalid nick `%s'\n"), nickstring); |
1238 | GNUNET_SCHEDULER_shutdown (); | ||
1239 | ret = 1; | 1417 | ret = 1; |
1418 | finish_command (); | ||
1240 | return; | 1419 | return; |
1241 | } | 1420 | } |
1242 | add = 1; | 1421 | add = 1; |
@@ -1258,8 +1437,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1258 | _ ("Missing option `%s' for operation `%s'\n"), | 1437 | _ ("Missing option `%s' for operation `%s'\n"), |
1259 | "-z", | 1438 | "-z", |
1260 | _ ("add")); | 1439 | _ ("add")); |
1261 | GNUNET_SCHEDULER_shutdown (); | ||
1262 | ret = 1; | 1440 | ret = 1; |
1441 | finish_command (); | ||
1263 | return; | 1442 | return; |
1264 | } | 1443 | } |
1265 | if (NULL == name) | 1444 | if (NULL == name) |
@@ -1268,8 +1447,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1268 | _ ("Missing option `%s' for operation `%s'\n"), | 1447 | _ ("Missing option `%s' for operation `%s'\n"), |
1269 | "-n", | 1448 | "-n", |
1270 | _ ("add")); | 1449 | _ ("add")); |
1271 | GNUNET_SCHEDULER_shutdown (); | ||
1272 | ret = 1; | 1450 | ret = 1; |
1451 | finish_command (); | ||
1273 | return; | 1452 | return; |
1274 | } | 1453 | } |
1275 | if (NULL == typestring) | 1454 | if (NULL == typestring) |
@@ -1278,16 +1457,16 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1278 | _ ("Missing option `%s' for operation `%s'\n"), | 1457 | _ ("Missing option `%s' for operation `%s'\n"), |
1279 | "-t", | 1458 | "-t", |
1280 | _ ("add")); | 1459 | _ ("add")); |
1281 | GNUNET_SCHEDULER_shutdown (); | ||
1282 | ret = 1; | 1460 | ret = 1; |
1461 | finish_command (); | ||
1283 | return; | 1462 | return; |
1284 | } | 1463 | } |
1285 | type = GNUNET_GNSRECORD_typename_to_number (typestring); | 1464 | type = GNUNET_GNSRECORD_typename_to_number (typestring); |
1286 | if (UINT32_MAX == type) | 1465 | if (UINT32_MAX == type) |
1287 | { | 1466 | { |
1288 | fprintf (stderr, _ ("Unsupported type `%s'\n"), typestring); | 1467 | fprintf (stderr, _ ("Unsupported type `%s'\n"), typestring); |
1289 | GNUNET_SCHEDULER_shutdown (); | ||
1290 | ret = 1; | 1468 | ret = 1; |
1469 | finish_command (); | ||
1291 | return; | 1470 | return; |
1292 | } | 1471 | } |
1293 | if ((GNUNET_DNSPARSER_TYPE_SRV == type) || | 1472 | if ((GNUNET_DNSPARSER_TYPE_SRV == type) || |
@@ -1297,8 +1476,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1297 | fprintf (stderr, | 1476 | fprintf (stderr, |
1298 | _ ("For DNS record types `SRV', `TLSA' and `OPENPGPKEY'")); | 1477 | _ ("For DNS record types `SRV', `TLSA' and `OPENPGPKEY'")); |
1299 | fprintf (stderr, ", please use a `BOX' record instead\n"); | 1478 | fprintf (stderr, ", please use a `BOX' record instead\n"); |
1300 | GNUNET_SCHEDULER_shutdown (); | ||
1301 | ret = 1; | 1479 | ret = 1; |
1480 | finish_command (); | ||
1302 | return; | 1481 | return; |
1303 | } | 1482 | } |
1304 | if (NULL == value) | 1483 | if (NULL == value) |
@@ -1308,7 +1487,7 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1308 | "-V", | 1487 | "-V", |
1309 | _ ("add")); | 1488 | _ ("add")); |
1310 | ret = 1; | 1489 | ret = 1; |
1311 | GNUNET_SCHEDULER_shutdown (); | 1490 | finish_command (); |
1312 | return; | 1491 | return; |
1313 | } | 1492 | } |
1314 | if (GNUNET_OK != | 1493 | if (GNUNET_OK != |
@@ -1318,8 +1497,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1318 | _ ("Value `%s' invalid for record type `%s'\n"), | 1497 | _ ("Value `%s' invalid for record type `%s'\n"), |
1319 | value, | 1498 | value, |
1320 | typestring); | 1499 | typestring); |
1321 | GNUNET_SCHEDULER_shutdown (); | ||
1322 | ret = 1; | 1500 | ret = 1; |
1501 | finish_command (); | ||
1323 | return; | 1502 | return; |
1324 | } | 1503 | } |
1325 | if (NULL == expirationstring) | 1504 | if (NULL == expirationstring) |
@@ -1328,15 +1507,15 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1328 | _ ("Missing option `%s' for operation `%s'\n"), | 1507 | _ ("Missing option `%s' for operation `%s'\n"), |
1329 | "-e", | 1508 | "-e", |
1330 | _ ("add")); | 1509 | _ ("add")); |
1331 | GNUNET_SCHEDULER_shutdown (); | ||
1332 | ret = 1; | 1510 | ret = 1; |
1511 | finish_command (); | ||
1333 | return; | 1512 | return; |
1334 | } | 1513 | } |
1335 | if (GNUNET_OK != parse_expiration (expirationstring, &etime_is_rel, &etime)) | 1514 | if (GNUNET_OK != parse_expiration (expirationstring, &etime_is_rel, &etime)) |
1336 | { | 1515 | { |
1337 | fprintf (stderr, _ ("Invalid time format `%s'\n"), expirationstring); | 1516 | fprintf (stderr, _ ("Invalid time format `%s'\n"), expirationstring); |
1338 | GNUNET_SCHEDULER_shutdown (); | ||
1339 | ret = 1; | 1517 | ret = 1; |
1518 | finish_command (); | ||
1340 | return; | 1519 | return; |
1341 | } | 1520 | } |
1342 | add_qe = GNUNET_NAMESTORE_records_lookup (ns, | 1521 | add_qe = GNUNET_NAMESTORE_records_lookup (ns, |
@@ -1355,8 +1534,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1355 | _ ("Missing option `%s' for operation `%s'\n"), | 1534 | _ ("Missing option `%s' for operation `%s'\n"), |
1356 | "-z", | 1535 | "-z", |
1357 | _ ("del")); | 1536 | _ ("del")); |
1358 | GNUNET_SCHEDULER_shutdown (); | ||
1359 | ret = 1; | 1537 | ret = 1; |
1538 | finish_command (); | ||
1360 | return; | 1539 | return; |
1361 | } | 1540 | } |
1362 | if (NULL == name) | 1541 | if (NULL == name) |
@@ -1365,8 +1544,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1365 | _ ("Missing option `%s' for operation `%s'\n"), | 1544 | _ ("Missing option `%s' for operation `%s'\n"), |
1366 | "-n", | 1545 | "-n", |
1367 | _ ("del")); | 1546 | _ ("del")); |
1368 | GNUNET_SCHEDULER_shutdown (); | ||
1369 | ret = 1; | 1547 | ret = 1; |
1548 | finish_command (); | ||
1370 | return; | 1549 | return; |
1371 | } | 1550 | } |
1372 | del_qe = GNUNET_NAMESTORE_records_lookup (ns, | 1551 | del_qe = GNUNET_NAMESTORE_records_lookup (ns, |
@@ -1398,8 +1577,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1398 | _ ("Missing option `%s' for operation `%s'\n"), | 1577 | _ ("Missing option `%s' for operation `%s'\n"), |
1399 | "-z", | 1578 | "-z", |
1400 | _ ("purge-zone")); | 1579 | _ ("purge-zone")); |
1401 | GNUNET_SCHEDULER_shutdown (); | ||
1402 | ret = 1; | 1580 | ret = 1; |
1581 | finish_command (); | ||
1403 | return; | 1582 | return; |
1404 | } | 1583 | } |
1405 | list_it = GNUNET_NAMESTORE_zone_iteration_start2 (ns, | 1584 | list_it = GNUNET_NAMESTORE_zone_iteration_start2 (ns, |
@@ -1423,8 +1602,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1423 | _ ("Missing option `%s' for operation `%s'\n"), | 1602 | _ ("Missing option `%s' for operation `%s'\n"), |
1424 | "-z", | 1603 | "-z", |
1425 | _ ("list")); | 1604 | _ ("list")); |
1426 | GNUNET_SCHEDULER_shutdown (); | ||
1427 | ret = 1; | 1605 | ret = 1; |
1606 | finish_command (); | ||
1428 | return; | 1607 | return; |
1429 | } | 1608 | } |
1430 | get_qe = GNUNET_NAMESTORE_records_lookup (ns, | 1609 | get_qe = GNUNET_NAMESTORE_records_lookup (ns, |
@@ -1457,8 +1636,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1457 | _ ("Missing option `%s' for operation `%s'\n"), | 1636 | _ ("Missing option `%s' for operation `%s'\n"), |
1458 | "-z", | 1637 | "-z", |
1459 | _ ("reverse-pkey")); | 1638 | _ ("reverse-pkey")); |
1460 | GNUNET_SCHEDULER_shutdown (); | ||
1461 | ret = 1; | 1639 | ret = 1; |
1640 | finish_command (); | ||
1462 | return; | 1641 | return; |
1463 | } | 1642 | } |
1464 | if (GNUNET_OK != | 1643 | if (GNUNET_OK != |
@@ -1468,7 +1647,9 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1468 | fprintf (stderr, | 1647 | fprintf (stderr, |
1469 | _ ("Invalid public key for reverse lookup `%s'\n"), | 1648 | _ ("Invalid public key for reverse lookup `%s'\n"), |
1470 | reverse_pkey); | 1649 | reverse_pkey); |
1471 | GNUNET_SCHEDULER_shutdown (); | 1650 | ret = 1; |
1651 | finish_command (); | ||
1652 | return; | ||
1472 | } | 1653 | } |
1473 | reverse_qe = GNUNET_NAMESTORE_zone_to_name (ns, | 1654 | reverse_qe = GNUNET_NAMESTORE_zone_to_name (ns, |
1474 | &zone_pkey, | 1655 | &zone_pkey, |
@@ -1489,8 +1670,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1489 | _ ("Missing option `%s' for operation `%s'\n"), | 1670 | _ ("Missing option `%s' for operation `%s'\n"), |
1490 | "-z", | 1671 | "-z", |
1491 | _ ("uri")); | 1672 | _ ("uri")); |
1492 | GNUNET_SCHEDULER_shutdown (); | ||
1493 | ret = 1; | 1673 | ret = 1; |
1674 | finish_command (); | ||
1494 | return; | 1675 | return; |
1495 | } | 1676 | } |
1496 | 1677 | ||
@@ -1502,8 +1683,8 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1502 | GNUNET_IDENTITY_public_key_from_string (sh, &pkey))) | 1683 | GNUNET_IDENTITY_public_key_from_string (sh, &pkey))) |
1503 | { | 1684 | { |
1504 | fprintf (stderr, _ ("Invalid URI `%s'\n"), uri); | 1685 | fprintf (stderr, _ ("Invalid URI `%s'\n"), uri); |
1505 | GNUNET_SCHEDULER_shutdown (); | ||
1506 | ret = 1; | 1686 | ret = 1; |
1687 | finish_command (); | ||
1507 | return; | 1688 | return; |
1508 | } | 1689 | } |
1509 | if (NULL == expirationstring) | 1690 | if (NULL == expirationstring) |
@@ -1512,15 +1693,15 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1512 | _ ("Missing option `%s' for operation `%s'\n"), | 1693 | _ ("Missing option `%s' for operation `%s'\n"), |
1513 | "-e", | 1694 | "-e", |
1514 | _ ("add")); | 1695 | _ ("add")); |
1515 | GNUNET_SCHEDULER_shutdown (); | ||
1516 | ret = 1; | 1696 | ret = 1; |
1697 | finish_command (); | ||
1517 | return; | 1698 | return; |
1518 | } | 1699 | } |
1519 | if (GNUNET_OK != parse_expiration (expirationstring, &etime_is_rel, &etime)) | 1700 | if (GNUNET_OK != parse_expiration (expirationstring, &etime_is_rel, &etime)) |
1520 | { | 1701 | { |
1521 | fprintf (stderr, _ ("Invalid time format `%s'\n"), expirationstring); | 1702 | fprintf (stderr, _ ("Invalid time format `%s'\n"), expirationstring); |
1522 | GNUNET_SCHEDULER_shutdown (); | ||
1523 | ret = 1; | 1703 | ret = 1; |
1704 | finish_command (); | ||
1524 | return; | 1705 | return; |
1525 | } | 1706 | } |
1526 | memset (&rd, 0, sizeof(rd)); | 1707 | memset (&rd, 0, sizeof(rd)); |
@@ -1556,34 +1737,155 @@ run_with_zone_pkey (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
1556 | } | 1737 | } |
1557 | } | 1738 | } |
1558 | 1739 | ||
1740 | #define MAX_LINE_LEN 4086 | ||
1741 | |||
1742 | #define MAX_ARGS 20 | ||
1743 | |||
1744 | static int | ||
1745 | get_identity_for_string (const char *str, | ||
1746 | struct GNUNET_IDENTITY_PrivateKey *zk) | ||
1747 | { | ||
1748 | const struct GNUNET_IDENTITY_PrivateKey *privkey; | ||
1749 | struct GNUNET_IDENTITY_PublicKey pubkey; | ||
1750 | struct GNUNET_IDENTITY_PublicKey ego_pubkey; | ||
1751 | struct EgoEntry *ego_entry; | ||
1752 | |||
1753 | if (GNUNET_OK == GNUNET_IDENTITY_public_key_from_string (str, | ||
1754 | &pubkey)) | ||
1755 | { | ||
1756 | for (ego_entry = ego_head; | ||
1757 | NULL != ego_entry; ego_entry = ego_entry->next) | ||
1758 | { | ||
1759 | privkey = GNUNET_IDENTITY_ego_get_private_key (ego_entry->ego); | ||
1760 | GNUNET_IDENTITY_ego_get_public_key (ego_entry->ego, &ego_pubkey); | ||
1761 | if (0 == memcmp (&ego_pubkey, &pubkey, sizeof (pubkey))) | ||
1762 | { | ||
1763 | *zk = *privkey; | ||
1764 | return GNUNET_OK; | ||
1765 | } | ||
1766 | } | ||
1767 | } | ||
1768 | else | ||
1769 | { | ||
1770 | for (ego_entry = ego_head; NULL != ego_entry; ego_entry = ego_entry->next) | ||
1771 | { | ||
1772 | /** FIXME: Check for zTLD? **/ | ||
1773 | if (0 != strcmp (str, ego_entry->identifier)) | ||
1774 | continue; | ||
1775 | *zk = *GNUNET_IDENTITY_ego_get_private_key (ego_entry->ego); | ||
1776 | return GNUNET_OK; | ||
1777 | } | ||
1778 | } | ||
1779 | return GNUNET_NO; | ||
1780 | } | ||
1559 | 1781 | ||
1560 | /** | ||
1561 | * Callback invoked from identity service with ego information. | ||
1562 | * An @a ego of NULL means the ego was not found. | ||
1563 | * | ||
1564 | * @param cls closure with the configuration | ||
1565 | * @param ego an ego known to identity service, or NULL | ||
1566 | */ | ||
1567 | static void | 1782 | static void |
1568 | identity_cb (void *cls, struct GNUNET_IDENTITY_Ego *ego) | 1783 | process_command_stdin () |
1569 | { | 1784 | { |
1570 | const struct GNUNET_CONFIGURATION_Handle *cfg = cls; | 1785 | char buf[MAX_LINE_LEN]; |
1786 | static struct GNUNET_IDENTITY_PrivateKey next_zone_key; | ||
1787 | static char next_name[GNUNET_DNSPARSER_MAX_NAME_LENGTH]; | ||
1788 | static int finished = GNUNET_NO; | ||
1789 | static int have_next_zonekey = GNUNET_NO; | ||
1790 | int zonekey_set = GNUNET_NO; | ||
1791 | char *tmp; | ||
1571 | 1792 | ||
1572 | el = NULL; | ||
1573 | 1793 | ||
1574 | if (NULL == ego) | 1794 | if (GNUNET_YES == have_next_zonekey) |
1795 | { | ||
1796 | zone_pkey = next_zone_key; | ||
1797 | if (NULL != name) | ||
1798 | GNUNET_free (name); | ||
1799 | name = GNUNET_strdup (next_name); | ||
1800 | zonekey_set = GNUNET_YES; | ||
1801 | } | ||
1802 | while (NULL != fgets (buf, sizeof (buf), stdin)) | ||
1575 | { | 1803 | { |
1576 | if (NULL != ego_name) | 1804 | if (1 >= strlen (buf)) |
1805 | continue; | ||
1806 | if (buf[strlen (buf) - 1] == '\n') | ||
1807 | buf[strlen (buf) - 1] = '\0'; | ||
1808 | /** | ||
1809 | * Check if this is a new name. If yes, and we have records, store them. | ||
1810 | */ | ||
1811 | if (buf[strlen (buf) - 1] == ':') | ||
1577 | { | 1812 | { |
1578 | fprintf (stderr, | 1813 | memset (next_name, 0, sizeof (next_name)); |
1579 | _ ("Ego `%s' not known to identity service\n"), | 1814 | strncpy (next_name, buf, strlen (buf) - 1); |
1580 | ego_name); | 1815 | tmp = strchr (next_name, '.'); |
1816 | if (NULL == tmp) | ||
1817 | { | ||
1818 | fprintf (stderr, "Error parsing name `%s'\n", next_name); | ||
1819 | ns_qe = GNUNET_NAMESTORE_transaction_commit (ns, &commit_cb, NULL); | ||
1820 | ret = 1; | ||
1821 | return; | ||
1822 | } | ||
1823 | if (GNUNET_OK != get_identity_for_string (tmp + 1, &next_zone_key)) | ||
1824 | { | ||
1825 | fprintf (stderr, "Error parsing zone name `%s'\n", tmp + 1); | ||
1826 | ret = 1; | ||
1827 | GNUNET_SCHEDULER_shutdown (); | ||
1828 | return; | ||
1829 | } | ||
1830 | *tmp = '\0'; | ||
1831 | printf ("Switching to new name `%s' in zone `%s'\n", next_name, tmp + 1); | ||
1832 | have_next_zonekey = GNUNET_YES; | ||
1833 | /* Run a command for the previous record set */ | ||
1834 | if (NULL != recordset) | ||
1835 | { | ||
1836 | run_with_zone_pkey (cfg); | ||
1837 | return; | ||
1838 | } | ||
1839 | zone_pkey = next_zone_key; | ||
1840 | if (NULL != name) | ||
1841 | GNUNET_free (name); | ||
1842 | name = GNUNET_strdup (next_name); | ||
1843 | zonekey_set = GNUNET_YES; | ||
1844 | continue; | ||
1581 | } | 1845 | } |
1846 | if (GNUNET_NO == zonekey_set) | ||
1847 | { | ||
1848 | fprintf (stderr, "Warning, encountered recordline without zone\n"); | ||
1849 | continue; | ||
1850 | } | ||
1851 | printf ("Parsing `%s'\n", buf); | ||
1852 | parse_recordline (buf); | ||
1853 | } | ||
1854 | if (GNUNET_NO == finished) | ||
1855 | { | ||
1856 | if (GNUNET_NO == zonekey_set) | ||
1857 | { | ||
1858 | fprintf (stderr, "Warning, encountered recordline without zone\n"); | ||
1859 | } | ||
1860 | else if (NULL != recordset) | ||
1861 | { | ||
1862 | run_with_zone_pkey (cfg); /** one last time **/ | ||
1863 | finished = GNUNET_YES; | ||
1864 | return; | ||
1865 | } | ||
1866 | } | ||
1867 | ns_qe = GNUNET_NAMESTORE_transaction_commit (ns, &commit_cb, NULL); | ||
1868 | return; | ||
1869 | } | ||
1870 | |||
1871 | |||
1872 | static void | ||
1873 | begin_cb (void *cls, enum GNUNET_ErrorCode ec) | ||
1874 | { | ||
1875 | ns_qe = NULL; | ||
1876 | if (GNUNET_EC_NONE != ec) | ||
1877 | { | ||
1878 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
1879 | "Failed to start transaction: %s\n", | ||
1880 | GNUNET_ErrorCode_get_hint (ec)); | ||
1582 | GNUNET_SCHEDULER_shutdown (); | 1881 | GNUNET_SCHEDULER_shutdown (); |
1583 | ret = -1; | ||
1584 | return; | 1882 | return; |
1585 | } | 1883 | } |
1586 | zone_pkey = *GNUNET_IDENTITY_ego_get_private_key (ego); | 1884 | if (read_from_stdin) |
1885 | { | ||
1886 | process_command_stdin (); | ||
1887 | return; | ||
1888 | } | ||
1587 | run_with_zone_pkey (cfg); | 1889 | run_with_zone_pkey (cfg); |
1588 | } | 1890 | } |
1589 | 1891 | ||
@@ -1606,7 +1908,6 @@ id_connect_cb (void *cls, | |||
1606 | void **ctx, | 1908 | void **ctx, |
1607 | const char *name) | 1909 | const char *name) |
1608 | { | 1910 | { |
1609 | const struct GNUNET_CONFIGURATION_Handle *cfg = cls; | ||
1610 | struct GNUNET_IDENTITY_PublicKey pk; | 1911 | struct GNUNET_IDENTITY_PublicKey pk; |
1611 | struct EgoEntry *ego_entry; | 1912 | struct EgoEntry *ego_entry; |
1612 | 1913 | ||
@@ -1621,17 +1922,20 @@ id_connect_cb (void *cls, | |||
1621 | GNUNET_CONTAINER_DLL_insert_tail (ego_head, | 1922 | GNUNET_CONTAINER_DLL_insert_tail (ego_head, |
1622 | ego_tail, | 1923 | ego_tail, |
1623 | ego_entry); | 1924 | ego_entry); |
1925 | if ((NULL != ego_name) && | ||
1926 | (0 == strcmp (name, ego_name))) | ||
1927 | zone_pkey = *GNUNET_IDENTITY_ego_get_private_key (ego); | ||
1624 | return; | 1928 | return; |
1625 | } | 1929 | } |
1626 | if (NULL != ego) | 1930 | if (NULL != ego) |
1627 | return; | 1931 | return; |
1628 | if (NULL == ego_name) | 1932 | ns_qe = GNUNET_NAMESTORE_transaction_begin (ns, &begin_cb, (void *) cfg); |
1629 | run_with_zone_pkey (cfg); | ||
1630 | else | ||
1631 | el = GNUNET_IDENTITY_ego_lookup (cfg, ego_name, &identity_cb, (void *) cfg); | ||
1632 | } | 1933 | } |
1633 | 1934 | ||
1634 | 1935 | ||
1936 | |||
1937 | |||
1938 | |||
1635 | /** | 1939 | /** |
1636 | * Main function that will be run. | 1940 | * Main function that will be run. |
1637 | * | 1941 | * |
@@ -1644,202 +1948,36 @@ static void | |||
1644 | run (void *cls, | 1948 | run (void *cls, |
1645 | char *const *args, | 1949 | char *const *args, |
1646 | const char *cfgfile, | 1950 | const char *cfgfile, |
1647 | const struct GNUNET_CONFIGURATION_Handle *cfg) | 1951 | const struct GNUNET_CONFIGURATION_Handle *_cfg) |
1648 | { | 1952 | { |
1649 | const char *pkey_str; | ||
1650 | |||
1651 | (void) cls; | 1953 | (void) cls; |
1652 | (void) args; | 1954 | (void) args; |
1653 | (void) cfgfile; | 1955 | (void) cfgfile; |
1956 | cfg = _cfg; | ||
1654 | if (NULL != args[0]) | 1957 | if (NULL != args[0]) |
1655 | GNUNET_log ( | 1958 | GNUNET_log ( |
1656 | GNUNET_ERROR_TYPE_WARNING, | 1959 | GNUNET_ERROR_TYPE_WARNING, |
1657 | _ ("Superfluous command line arguments (starting with `%s') ignored\n"), | 1960 | _ ("Superfluous command line arguments (starting with `%s') ignored\n"), |
1658 | args[0]); | 1961 | args[0]); |
1659 | if ((NULL != args[0]) && (NULL == uri)) | ||
1660 | uri = GNUNET_strdup (args[0]); | ||
1661 | 1962 | ||
1662 | GNUNET_SCHEDULER_add_shutdown (&do_shutdown, (void *) cfg); | 1963 | GNUNET_SCHEDULER_add_shutdown (&do_shutdown, (void *) cfg); |
1663 | pkey_str = getenv ("GNUNET_NAMESTORE_EGO_PRIVATE_KEY"); | 1964 | ns = GNUNET_NAMESTORE_connect (cfg); |
1664 | if (NULL != pkey_str) | 1965 | if (NULL == ns) |
1665 | { | 1966 | { |
1666 | if (GNUNET_OK != GNUNET_STRINGS_string_to_data (pkey_str, | 1967 | fprintf (stderr, _ ("Failed to connect to namestore\n")); |
1667 | strlen (pkey_str), | 1968 | GNUNET_SCHEDULER_shutdown (); |
1668 | &zone_pkey, | ||
1669 | sizeof(zone_pkey))) | ||
1670 | { | ||
1671 | fprintf (stderr, | ||
1672 | "Malformed private key `%s' in $%s\n", | ||
1673 | pkey_str, | ||
1674 | "GNUNET_NAMESTORE_EGO_PRIVATE_KEY"); | ||
1675 | ret = 1; | ||
1676 | GNUNET_SCHEDULER_shutdown (); | ||
1677 | return; | ||
1678 | } | ||
1679 | run_with_zone_pkey (cfg); | ||
1680 | return; | 1969 | return; |
1681 | } | 1970 | } |
1682 | idh = GNUNET_IDENTITY_connect (cfg, &id_connect_cb, (void *) cfg); | 1971 | idh = GNUNET_IDENTITY_connect (cfg, &id_connect_cb, (void *) cfg); |
1683 | if (NULL == idh) | 1972 | if (NULL == idh) |
1684 | fprintf (stderr, _ ("Cannot connect to identity service\n")); | ||
1685 | ret = -1; | ||
1686 | } | ||
1687 | |||
1688 | |||
1689 | /** | ||
1690 | * Command-line option parser function that allows the user to specify | ||
1691 | * a complete record as one argument for adding/removing. A pointer | ||
1692 | * to the head of the list of record sets must be passed as the "scls" | ||
1693 | * argument. | ||
1694 | * | ||
1695 | * @param ctx command line processor context | ||
1696 | * @param scls must be of type "struct GNUNET_FS_Uri **" | ||
1697 | * @param option name of the option (typically 'R') | ||
1698 | * @param value command line argument given; format is | ||
1699 | * "TTL TYPE FLAGS VALUE" where TTL is an expiration time (rel or abs), | ||
1700 | * always given in seconds (without the unit), | ||
1701 | * TYPE is a DNS/GNS record type, FLAGS is either "n" for no flags or | ||
1702 | * a combination of 's' (shadow) and 'p' (public) and VALUE is the | ||
1703 | * value (in human-readable format) | ||
1704 | * @return #GNUNET_OK on success | ||
1705 | */ | ||
1706 | static int | ||
1707 | multirecord_process (struct GNUNET_GETOPT_CommandLineProcessorContext *ctx, | ||
1708 | void *scls, | ||
1709 | const char *option, | ||
1710 | const char *value) | ||
1711 | { | ||
1712 | struct RecordSetEntry **head = scls; | ||
1713 | struct RecordSetEntry *r; | ||
1714 | struct GNUNET_GNSRECORD_Data record; | ||
1715 | char *cp; | ||
1716 | char *tok; | ||
1717 | char *saveptr; | ||
1718 | int etime_is_rel; | ||
1719 | void *raw_data; | ||
1720 | |||
1721 | (void) ctx; | ||
1722 | (void) option; | ||
1723 | cp = GNUNET_strdup (value); | ||
1724 | tok = strtok_r (cp, " ", &saveptr); | ||
1725 | if (NULL == tok) | ||
1726 | { | ||
1727 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
1728 | _ ("Empty record line argument is not allowed.\n")); | ||
1729 | GNUNET_free (cp); | ||
1730 | return GNUNET_SYSERR; | ||
1731 | } | ||
1732 | { | ||
1733 | char *etime_in_s; | ||
1734 | |||
1735 | GNUNET_asprintf (&etime_in_s, "%s s", tok); | ||
1736 | if (GNUNET_OK != | ||
1737 | parse_expiration (etime_in_s, &etime_is_rel, &record.expiration_time)) | ||
1738 | { | ||
1739 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
1740 | _ ("Invalid expiration time `%s' (must be without unit)\n"), | ||
1741 | tok); | ||
1742 | GNUNET_free (cp); | ||
1743 | GNUNET_free (etime_in_s); | ||
1744 | return GNUNET_SYSERR; | ||
1745 | } | ||
1746 | GNUNET_free (etime_in_s); | ||
1747 | } | ||
1748 | tok = strtok_r (NULL, " ", &saveptr); | ||
1749 | if (NULL == tok) | ||
1750 | { | ||
1751 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
1752 | _ ("Missing entries in record line `%s'.\n"), | ||
1753 | value); | ||
1754 | GNUNET_free (cp); | ||
1755 | return GNUNET_SYSERR; | ||
1756 | } | ||
1757 | record.record_type = GNUNET_GNSRECORD_typename_to_number (tok); | ||
1758 | if (UINT32_MAX == record.record_type) | ||
1759 | { | ||
1760 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _ ("Unknown record type `%s'\n"), tok); | ||
1761 | GNUNET_free (cp); | ||
1762 | return GNUNET_SYSERR; | ||
1763 | } | ||
1764 | tok = strtok_r (NULL, " ", &saveptr); | ||
1765 | if (NULL == tok) | ||
1766 | { | ||
1767 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
1768 | _ ("Missing entries in record line `%s'.\n"), | ||
1769 | value); | ||
1770 | GNUNET_free (cp); | ||
1771 | return GNUNET_SYSERR; | ||
1772 | } | ||
1773 | record.flags = GNUNET_GNSRECORD_RF_NONE; | ||
1774 | if (etime_is_rel) | ||
1775 | record.flags |= GNUNET_GNSRECORD_RF_RELATIVE_EXPIRATION; | ||
1776 | if (NULL == strchr (tok, (unsigned char) 'p')) /* p = public */ | ||
1777 | record.flags |= GNUNET_GNSRECORD_RF_PRIVATE; | ||
1778 | if (NULL != strchr (tok, (unsigned char) 's')) | ||
1779 | record.flags |= GNUNET_GNSRECORD_RF_SHADOW; | ||
1780 | /* find beginning of record value */ | ||
1781 | tok = strchr (&value[tok - cp], (unsigned char) ' '); | ||
1782 | if (NULL == tok) | ||
1783 | { | ||
1784 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
1785 | _ ("Missing entries in record line `%s'.\n"), | ||
1786 | value); | ||
1787 | GNUNET_free (cp); | ||
1788 | return GNUNET_SYSERR; | ||
1789 | } | ||
1790 | GNUNET_free (cp); | ||
1791 | tok++; /* skip space */ | ||
1792 | if (GNUNET_OK != GNUNET_GNSRECORD_string_to_value (record.record_type, | ||
1793 | tok, | ||
1794 | &raw_data, | ||
1795 | &record.data_size)) | ||
1796 | { | 1973 | { |
1797 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | 1974 | ret = -1; |
1798 | _ ("Invalid record data for type %s: `%s'.\n"), | 1975 | fprintf (stderr, _ ("Cannot connect to identity service\n")); |
1799 | GNUNET_GNSRECORD_number_to_typename (record.record_type), | 1976 | GNUNET_SCHEDULER_shutdown (); |
1800 | tok); | ||
1801 | return GNUNET_SYSERR; | ||
1802 | } | 1977 | } |
1803 | |||
1804 | r = GNUNET_malloc (sizeof(struct RecordSetEntry) + record.data_size); | ||
1805 | r->next = *head; | ||
1806 | record.data = &r[1]; | ||
1807 | memcpy (&r[1], raw_data, record.data_size); | ||
1808 | GNUNET_free (raw_data); | ||
1809 | r->record = record; | ||
1810 | *head = r; | ||
1811 | return GNUNET_OK; | ||
1812 | } | 1978 | } |
1813 | 1979 | ||
1814 | 1980 | ||
1815 | /** | ||
1816 | * Allow user to specify keywords. | ||
1817 | * | ||
1818 | * @param shortName short name of the option | ||
1819 | * @param name long name of the option | ||
1820 | * @param argumentHelp help text for the option argument | ||
1821 | * @param description long help text for the option | ||
1822 | * @param[out] topKeywords set to the desired value | ||
1823 | */ | ||
1824 | struct GNUNET_GETOPT_CommandLineOption | ||
1825 | multirecord_option (char shortName, | ||
1826 | const char *name, | ||
1827 | const char *argumentHelp, | ||
1828 | const char *description, | ||
1829 | struct RecordSetEntry **rs) | ||
1830 | { | ||
1831 | struct GNUNET_GETOPT_CommandLineOption clo = { .shortName = shortName, | ||
1832 | .name = name, | ||
1833 | .argumentHelp = argumentHelp, | ||
1834 | .description = description, | ||
1835 | .require_argument = 1, | ||
1836 | .processor = | ||
1837 | &multirecord_process, | ||
1838 | .scls = (void *) rs }; | ||
1839 | |||
1840 | return clo; | ||
1841 | } | ||
1842 | |||
1843 | 1981 | ||
1844 | /** | 1982 | /** |
1845 | * The main function for gnunet-namestore. | 1983 | * The main function for gnunet-namestore. |
@@ -1851,6 +1989,7 @@ multirecord_option (char shortName, | |||
1851 | int | 1989 | int |
1852 | main (int argc, char *const *argv) | 1990 | main (int argc, char *const *argv) |
1853 | { | 1991 | { |
1992 | int lret; | ||
1854 | struct GNUNET_GETOPT_CommandLineOption options[] = | 1993 | struct GNUNET_GETOPT_CommandLineOption options[] = |
1855 | { GNUNET_GETOPT_option_flag ('a', "add", gettext_noop ("add record"), &add), | 1994 | { GNUNET_GETOPT_option_flag ('a', "add", gettext_noop ("add record"), &add), |
1856 | GNUNET_GETOPT_option_flag ('d', | 1995 | GNUNET_GETOPT_option_flag ('d', |
@@ -1861,6 +2000,10 @@ main (int argc, char *const *argv) | |||
1861 | "display", | 2000 | "display", |
1862 | gettext_noop ("display records"), | 2001 | gettext_noop ("display records"), |
1863 | &list), | 2002 | &list), |
2003 | GNUNET_GETOPT_option_flag ('S', | ||
2004 | "from-stdin", | ||
2005 | gettext_noop ("read commands from stdin"), | ||
2006 | &read_from_stdin), | ||
1864 | GNUNET_GETOPT_option_string ( | 2007 | GNUNET_GETOPT_option_string ( |
1865 | 'e', | 2008 | 'e', |
1866 | "expiration", | 2009 | "expiration", |
@@ -1885,19 +2028,16 @@ main (int argc, char *const *argv) | |||
1885 | gettext_noop ( | 2028 | gettext_noop ( |
1886 | "name of the record to add/delete/display"), | 2029 | "name of the record to add/delete/display"), |
1887 | &name), | 2030 | &name), |
1888 | GNUNET_GETOPT_option_string ('r', | 2031 | GNUNET_GETOPT_option_flag ('r', |
1889 | "reverse", | 2032 | "recordline", |
1890 | "PKEY", | 2033 | gettext_noop ("Output in recordline format"), |
2034 | &output_recordline), | ||
2035 | GNUNET_GETOPT_option_string ('Z', | ||
2036 | "zone-to-name", | ||
2037 | "KEY", | ||
1891 | gettext_noop ( | 2038 | gettext_noop ( |
1892 | "determine our name for the given PKEY"), | 2039 | "determine our name for the given KEY"), |
1893 | &reverse_pkey), | 2040 | &reverse_pkey), |
1894 | multirecord_option ( | ||
1895 | 'R', | ||
1896 | "replace", | ||
1897 | "RECORDLINE", | ||
1898 | gettext_noop ( | ||
1899 | "set record set to values given by (possibly multiple) RECORDLINES; can be specified multiple times"), | ||
1900 | &recordset), | ||
1901 | GNUNET_GETOPT_option_string ('t', | 2041 | GNUNET_GETOPT_option_string ('t', |
1902 | "type", | 2042 | "type", |
1903 | "TYPE", | 2043 | "TYPE", |
@@ -1956,7 +2096,7 @@ main (int argc, char *const *argv) | |||
1956 | "name of the ego controlling the zone"), | 2096 | "name of the ego controlling the zone"), |
1957 | &ego_name), | 2097 | &ego_name), |
1958 | GNUNET_GETOPT_OPTION_END }; | 2098 | GNUNET_GETOPT_OPTION_END }; |
1959 | int lret; | 2099 | |
1960 | 2100 | ||
1961 | if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) | 2101 | if (GNUNET_OK != GNUNET_STRINGS_get_utf8_args (argc, argv, &argc, &argv)) |
1962 | return 2; | 2102 | return 2; |
diff --git a/src/namestore/test_namestore_put_multiple.sh b/src/namestore/test_namestore_put_multiple.sh index f33fb1c3a..4c7340440 100644..100755 --- a/src/namestore/test_namestore_put_multiple.sh +++ b/src/namestore/test_namestore_put_multiple.sh | |||
@@ -24,25 +24,9 @@ if [ 0 -ne $ret ]; then | |||
24 | gnunet-identity -C randomtestingid | 24 | gnunet-identity -C randomtestingid |
25 | fi | 25 | fi |
26 | 26 | ||
27 | function minimize_ttl { | ||
28 | ttl=10000000 | ||
29 | arr=$1 | ||
30 | # parse each element and update ttl to smallest one | ||
31 | for i in "${arr[@]}" | ||
32 | do | ||
33 | currttl=$(echo -n "$i" | cut -d' ' -f1) | ||
34 | if [ "$currttl" -lt "$ttl" ] | ||
35 | then | ||
36 | ttl=$currttl | ||
37 | fi | ||
38 | |||
39 | done | ||
40 | echo "$ttl" | ||
41 | } | ||
42 | |||
43 | function get_record_type { | 27 | function get_record_type { |
44 | arr=$1 | 28 | arr=$1 |
45 | typ=$(echo -n "${arr[0]}" | cut -d' ' -f2) | 29 | typ=$(echo -n "${arr[0]}" | cut -d' ' -f1) |
46 | echo "$typ" | 30 | echo "$typ" |
47 | } | 31 | } |
48 | 32 | ||
@@ -59,10 +43,14 @@ function testing { | |||
59 | typ=$(get_record_type "${records[@]}") | 43 | typ=$(get_record_type "${records[@]}") |
60 | for i in "${records[@]}" | 44 | for i in "${records[@]}" |
61 | do | 45 | do |
62 | recordstring+="-R $i" | 46 | recordstring+="$i"$'\n' |
63 | done | 47 | done |
64 | #echo "$recordstring" | 48 | echo "$recordstring" |
65 | gnunet-namestore -z randomtestingid -n "$label" "$recordstring" 2>&1 /dev/null | 49 | gnunet-namestore -a -S <<EOF |
50 | $label.randomtestingid: | ||
51 | $recordstring | ||
52 | EOF | ||
53 | ret=$? | ||
66 | if [ 0 -ne $ret ]; then | 54 | if [ 0 -ne $ret ]; then |
67 | echo "failed to add record $label: $recordstring" | 55 | echo "failed to add record $label: $recordstring" |
68 | fi | 56 | fi |
@@ -75,26 +63,27 @@ function testing { | |||
75 | # TEST CASES | 63 | # TEST CASES |
76 | # 1 | 64 | # 1 |
77 | echo "Testing adding of single A record with -R" | 65 | echo "Testing adding of single A record with -R" |
66 | declare -a arr=('A 1200 [r] 127.0.0.1') | ||
78 | testing test1 "${arr[@]}" | 67 | testing test1 "${arr[@]}" |
79 | # 2 | 68 | # 2 |
80 | echo "Testing adding of multiple A records with -R" | 69 | echo "Testing adding of multiple A records with -R" |
81 | declare -a arr=('1200 A n 127.0.0.1' '2400 A n 127.0.0.2') | 70 | declare -a arr=('A 1200 [r] 127.0.0.1' 'A 2400 [r] 127.0.0.2') |
82 | testing test2 "${arr[@]}" | 71 | testing test2 "${arr[@]}" |
83 | # 3 | 72 | # 3 |
84 | echo "Testing adding of multiple different records with -R" | 73 | echo "Testing adding of multiple different records with -R" |
85 | declare -a arr=('1200 A n 127.0.0.1' '2400 AAAA n 2002::') | 74 | declare -a arr=('A 1200 [r] 127.0.0.1' 'AAAA 2400 [r] 2002::') |
86 | testing test3 "${arr[@]}" | 75 | testing test3 "${arr[@]}" |
87 | # 4 | 76 | # 4 |
88 | echo "Testing adding of single GNS2DNS record with -R" | 77 | echo "Testing adding of single GNS2DNS record with -R" |
89 | declare -a arr=('86400 GNS2DNS n gnu.org@127.0.0.1') | 78 | declare -a arr=('GNS2DNS 86400 [r] gnu.org@127.0.0.1') |
90 | testing test4 "${arr[@]}" | 79 | testing test4 "${arr[@]}" |
91 | # 5 | 80 | # 5 |
92 | echo "Testing adding of single GNS2DNS shadow record with -R" | 81 | echo "Testing adding of single GNS2DNS shadow record with -R" |
93 | declare -a arr=('86409 GNS2DNS s gnu.org@127.0.0.250') | 82 | declare -a arr=('GNS2DNS 86409 [rs] gnu.org@127.0.0.250') |
94 | testing test5 "${arr[@]}" | 83 | testing test5 "${arr[@]}" |
95 | # 6 | 84 | # 6 |
96 | echo "Testing adding of multiple GNS2DNS record with -R" | 85 | echo "Testing adding of multiple GNS2DNS record with -R" |
97 | declare -a arr=('1 GNS2DNS n gnunet.org@127.0.0.1' '3600 GNS2DNS s gnunet.org@127.0.0.2') | 86 | declare -a arr=('GNS2DNS 1 [r] gnunet.org@127.0.0.1' 'GNS2DNS 3600 [s] gnunet.org@127.0.0.2') |
98 | testing test6 "${arr[@]}" | 87 | testing test6 "${arr[@]}" |
99 | val=$(gnunet-gns -t GNS2DNS -u test6.randomtestingid) | 88 | val=$(gnunet-gns -t GNS2DNS -u test6.randomtestingid) |
100 | if [[ $val == *"127.0.0.1"* ]]; then | 89 | if [[ $val == *"127.0.0.1"* ]]; then |
@@ -108,16 +97,16 @@ if [[ $val == *"127.0.0.2"* ]]; then | |||
108 | fi | 97 | fi |
109 | # 7 | 98 | # 7 |
110 | echo "Testing adding MX record with -R" | 99 | echo "Testing adding MX record with -R" |
111 | declare -a arr=('3600 MX n 10,mail') | 100 | declare -a arr=('MX 3600 [r] 10,mail') |
112 | testing test7 "${arr[@]}" | 101 | testing test7 "${arr[@]}" |
113 | # 8 | 102 | # 8 |
114 | echo "Testing adding TXT record with -R" | 103 | echo "Testing adding TXT record with -R" |
115 | declare -a arr=('3600 TXT n Pretty_Unicorns') | 104 | declare -a arr=('TXT 3600 [r] Pretty_Unicorns') |
116 | testing test8 "${arr[@]}" | 105 | testing test8 "${arr[@]}" |
117 | # 8 | 106 | # 8 |
118 | echo "Testing adding TXT record with -R" | 107 | #echo "Testing adding TXT record with -R" |
119 | declare -a arr=('3600 SRV n _autodiscover_old._tcp.bfh.ch.') | 108 | #declare -a arr=('SRV 3600 [r] _autodiscover_old._tcp.bfh.ch.') |
120 | testing test8 "${arr[@]}" | 109 | #testing test8 "${arr[@]}" |
121 | 110 | ||
122 | # CLEANUP | 111 | # CLEANUP |
123 | gnunet-identity -D randomtestingid | 112 | gnunet-identity -D randomtestingid |
diff --git a/src/namestore/test_namestore_put_stdin.sh b/src/namestore/test_namestore_put_stdin.sh new file mode 100755 index 000000000..deb7bc4cb --- /dev/null +++ b/src/namestore/test_namestore_put_stdin.sh | |||
@@ -0,0 +1,68 @@ | |||
1 | #!/bin/bash | ||
2 | CONFIGURATION="test_namestore_api.conf" | ||
3 | trap "gnunet-arm -e -c $CONFIGURATION" SIGINT | ||
4 | |||
5 | LOCATION=$(which gnunet-config) | ||
6 | if [ -z $LOCATION ] | ||
7 | then | ||
8 | LOCATION="gnunet-config" | ||
9 | fi | ||
10 | $LOCATION --version 1> /dev/null | ||
11 | if test $? != 0 | ||
12 | then | ||
13 | echo "GNUnet command line tools cannot be found, check environmental variables PATH and GNUNET_PREFIX" | ||
14 | exit 77 | ||
15 | fi | ||
16 | |||
17 | rm -rf `$LOCATION -c $CONFIGURATION -s PATHS -o GNUNET_HOME` | ||
18 | TEST_RECORD_NAME="www3" | ||
19 | TEST_RECORD_NAME2="www" | ||
20 | TEST_IP="8.7.6.5" | ||
21 | TEST_IP2="1.2.3.4" | ||
22 | |||
23 | which timeout &> /dev/null && DO_TIMEOUT="timeout 5" | ||
24 | |||
25 | function start_peer | ||
26 | { | ||
27 | gnunet-arm -s -c $CONFIGURATION | ||
28 | gnunet-identity -C testego -c $CONFIGURATION | ||
29 | gnunet-identity -C testego2 -c $CONFIGURATION | ||
30 | } | ||
31 | |||
32 | function stop_peer | ||
33 | { | ||
34 | gnunet-identity -D testego -c $CONFIGURATION | ||
35 | gnunet-identity -D testego2 -c $CONFIGURATION | ||
36 | gnunet-arm -e -c $CONFIGURATION | ||
37 | } | ||
38 | |||
39 | |||
40 | start_peer | ||
41 | # Create a public record | ||
42 | EGOKEY=`gnunet-identity -d | grep testego2 | cut -d' ' -f3` | ||
43 | gnunet-namestore -a -c $CONFIGURATION -S <<EOF | ||
44 | $TEST_RECORD_NAME.testego: | ||
45 | A 3600000000 [pr] $TEST_IP | ||
46 | TXT 21438201833 [r] $TEST_IP2 | ||
47 | |||
48 | TXT 21438201833 [r] aslkdj asdlkjaslkd 232! | ||
49 | |||
50 | $TEST_RECORD_NAME2.testego: | ||
51 | AAAA 324241223 [prS] ::dead:beef | ||
52 | A 111324241223000000 [pC] 1.1.1.1 | ||
53 | |||
54 | www7.$EGOKEY: | ||
55 | A 3600000000 [pr] $TEST_IP | ||
56 | |||
57 | EOF | ||
58 | NAMESTORE_RES=$? | ||
59 | gnunet-namestore -D -r -c $CONFIGURATION | ||
60 | stop_peer | ||
61 | |||
62 | if [ $NAMESTORE_RES = 0 ] | ||
63 | then | ||
64 | echo "PASS: Creating name in namestore" | ||
65 | else | ||
66 | echo "FAIL: Creating name in namestore failed with $NAMESTORE_RES." | ||
67 | exit 1 | ||
68 | fi | ||