static void testNamespace () { struct GNUNET_CRYPTO_EcdsaPrivateKey *ns; struct GNUNET_FS_BlockOptions bo; struct GNUNET_CONTAINER_MetaData *meta; struct GNUNET_FS_Uri *ksk_uri; struct GNUNET_FS_Uri *sks_uri; ns = GNUNET_CRYPTO_ecdsa_key_create (); meta = GNUNET_CONTAINER_meta_data_create (); ksk_uri = GNUNET_FS_uri_parse ("gnunet://fs/ksk/testnsa", NULL); bo.content_priority = 1; bo.anonymity_level = 1; bo.replication_level = 0; bo.expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_MINUTES); sks_uri = GNUNET_FS_uri_sks_create (&nsid, "root"); GNUNET_FS_publish_ksk (fs, ksk_uri, meta, sks_uri, &bo, GNUNET_FS_PUBLISH_OPTION_NONE, &adv_cont, NULL); GNUNET_FS_uri_destroy (sks_uri); kill_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MINUTES, &do_timeout, NULL); GNUNET_FS_uri_destroy (ksk_uri); GNUNET_CONTAINER_meta_data_destroy (meta); GNUNET_free (ns); }
static void do_download (void *cls, const char *emsg) { struct DownloadContext *dc = cls; struct GNUNET_FS_Uri *uri = dc->uri; GNUNET_TESTBED_operation_done (op); op = NULL; if (NULL != dc->fn) { GNUNET_DISK_directory_remove (dc->fn); GNUNET_free (dc->fn); } GNUNET_free (dc); if (NULL != emsg) { GNUNET_SCHEDULER_shutdown (); GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failed to stop source daemon: %s\n", emsg); GNUNET_FS_uri_destroy (uri); ok = 1; return; } GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Downloading %llu bytes\n", (unsigned long long) FILESIZE); start_time = GNUNET_TIME_absolute_get (); GNUNET_FS_TEST_download (daemons[0], TIMEOUT, 1, SEED, uri, VERBOSE, &do_stop, NULL); GNUNET_FS_uri_destroy (uri); }
/** * Destroy publish-structure. Clients should never destroy publish * structures that were passed to #GNUNET_FS_publish_start already. * * @param fi structure to destroy * @param cleaner function to call on each entry in the structure * (useful to clean up client_info); can be NULL; return * values are ignored * @param cleaner_cls closure for @a cleaner */ void GNUNET_FS_file_information_destroy (struct GNUNET_FS_FileInformation *fi, GNUNET_FS_FileInformationProcessor cleaner, void *cleaner_cls) { struct GNUNET_FS_FileInformation *pos; int no; no = GNUNET_NO; if (GNUNET_YES == fi->is_directory) { /* clean up directory */ while (NULL != (pos = fi->data.dir.entries)) { fi->data.dir.entries = pos->next; GNUNET_FS_file_information_destroy (pos, cleaner, cleaner_cls); } /* clean up client-info */ if (NULL != cleaner) cleaner (cleaner_cls, fi, fi->data.dir.dir_size, fi->meta, &fi->keywords, &fi->bo, &no, &fi->client_info); GNUNET_free_non_null (fi->data.dir.dir_data); } else { /* call clean-up function of the reader */ if (NULL != fi->data.file.reader) { (void) fi->data.file.reader (fi->data.file.reader_cls, 0, 0, NULL, NULL); fi->data.file.reader = NULL; } /* clean up client-info */ if (NULL != cleaner) cleaner (cleaner_cls, fi, fi->data.file.file_size, fi->meta, &fi->keywords, &fi->bo, &fi->data.file.do_index, &fi->client_info); } GNUNET_free_non_null (fi->filename); GNUNET_free_non_null (fi->emsg); if (NULL != fi->sks_uri) GNUNET_FS_uri_destroy (fi->sks_uri); if (NULL != fi->chk_uri) GNUNET_FS_uri_destroy (fi->chk_uri); /* clean up serialization */ if ((NULL != fi->serialization) && (0 != UNLINK (fi->serialization))) GNUNET_log_strerror_file (GNUNET_ERROR_TYPE_WARNING, "unlink", fi->serialization); if (NULL != fi->keywords) GNUNET_FS_uri_destroy (fi->keywords); if (NULL != fi->meta) GNUNET_CONTAINER_meta_data_destroy (fi->meta); GNUNET_free_non_null (fi->serialization); if (NULL != fi->te) { GNUNET_FS_tree_encoder_finish (fi->te, NULL); fi->te = NULL; } GNUNET_free (fi); }
static void do_shutdown () { if (uri_this != NULL) GNUNET_FS_uri_destroy (uri_this); if (uri_next != NULL) GNUNET_FS_uri_destroy (uri_next); if (ns != NULL) GNUNET_free (ns); if (meta != NULL) GNUNET_CONTAINER_meta_data_destroy (meta); }
static void do_shutdown () { if (uri_this != NULL) GNUNET_FS_uri_destroy (uri_this); if (uri_next != NULL) GNUNET_FS_uri_destroy (uri_next); if (ns != NULL) GNUNET_FS_namespace_delete (ns, GNUNET_NO); if (meta != NULL) GNUNET_CONTAINER_meta_data_destroy (meta); }
/** * Main function that will be run by the scheduler. * * @param cls closure * @param args remaining command-line arguments * @param cfgfile name of the configuration file used (for saving, can be NULL!) * @param c configuration */ static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *c) { struct GNUNET_FS_Uri *uri; unsigned int argc; enum GNUNET_FS_SearchOptions options; argc = 0; while (NULL != args[argc]) argc++; uri = GNUNET_FS_uri_ksk_create_from_args (argc, (const char **) args); if (NULL == uri) { FPRINTF (stderr, "%s", _("Could not create keyword URI from arguments.\n")); ret = 1; return; } cfg = c; ctx = GNUNET_FS_start (cfg, "gnunet-search", &progress_cb, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); if (NULL == ctx) { FPRINTF (stderr, _("Could not initialize `%s' subsystem.\n"), "FS"); GNUNET_FS_uri_destroy (uri); ret = 1; return; } if (output_filename != NULL) db = GNUNET_FS_directory_builder_create (NULL); options = GNUNET_FS_SEARCH_OPTION_NONE; if (local_only) options |= GNUNET_FS_SEARCH_OPTION_LOOPBACK_ONLY; sc = GNUNET_FS_search_start (ctx, uri, anonymity, options, NULL); GNUNET_FS_uri_destroy (uri); if (NULL == sc) { FPRINTF (stderr, "%s", _("Could not start searching.\n")); GNUNET_FS_stop (ctx); ret = 1; return; } if (0 != timeout.rel_value_us) GNUNET_SCHEDULER_add_delayed (timeout, &shutdown_task, NULL); else GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); }
static void sks_cont (void *cls, const struct GNUNET_FS_Uri *uri, const char *emsg) { struct GNUNET_CONTAINER_MetaData *meta; struct GNUNET_FS_Uri *ksk_uri; char *msg; struct GNUNET_FS_BlockOptions bo; if (NULL == uri) { fprintf (stderr, "Error publishing: %s\n", emsg); err = 1; GNUNET_FS_stop (fs); return; } meta = GNUNET_CONTAINER_meta_data_create (); msg = NULL; ksk_uri = GNUNET_FS_uri_parse ("gnunet://fs/ksk/ns-search", &msg); GNUNET_assert (NULL == msg); ksk_expect_uri = GNUNET_FS_uri_dup (uri); bo.content_priority = 1; bo.anonymity_level = 1; bo.replication_level = 0; bo.expiration_time = GNUNET_TIME_relative_to_absolute (GNUNET_TIME_UNIT_MINUTES); GNUNET_FS_publish_ksk (fs, ksk_uri, meta, uri, &bo, GNUNET_FS_PUBLISH_OPTION_NONE, &publish_cont, NULL); GNUNET_FS_uri_destroy (ksk_uri); GNUNET_CONTAINER_meta_data_destroy (meta); }
/** * Create SUSPEND event for the given unindex operation * and then clean up our state (without stop signal). * * @param cls the `struct GNUNET_FS_UnindexContext` to signal for */ void GNUNET_FS_unindex_signal_suspend_ (void *cls) { struct GNUNET_FS_UnindexContext *uc = cls; struct GNUNET_FS_ProgressInfo pi; /* FIXME: lots of duplication with unindex_stop here! */ if (uc->dscan != NULL) { GNUNET_FS_directory_scan_abort (uc->dscan); uc->dscan = NULL; } if (NULL != uc->dqe) { GNUNET_DATASTORE_cancel (uc->dqe); uc->dqe = NULL; } if (uc->fhc != NULL) { GNUNET_CRYPTO_hash_file_cancel (uc->fhc); uc->fhc = NULL; } if (NULL != uc->ksk_uri) { GNUNET_FS_uri_destroy (uc->ksk_uri); uc->ksk_uri = NULL; } if (uc->client != NULL) { GNUNET_CLIENT_disconnect (uc->client); uc->client = NULL; } if (NULL != uc->dsh) { GNUNET_DATASTORE_disconnect (uc->dsh, GNUNET_NO); uc->dsh = NULL; } if (NULL != uc->tc) { GNUNET_FS_tree_encoder_finish (uc->tc, NULL); uc->tc = NULL; } if (uc->fh != NULL) { GNUNET_DISK_file_close (uc->fh); uc->fh = NULL; } GNUNET_FS_end_top (uc->h, uc->top); pi.status = GNUNET_FS_STATUS_UNINDEX_SUSPEND; GNUNET_FS_unindex_make_status_ (&pi, uc, (uc->state == UNINDEX_STATE_COMPLETE) ? uc->file_size : 0); GNUNET_break (NULL == uc->client_info); GNUNET_free (uc->filename); GNUNET_free_non_null (uc->serialization); GNUNET_free_non_null (uc->emsg); GNUNET_free (uc); }
static int testKeyword () { char *uri; struct GNUNET_FS_Uri *ret; char *emsg; if (NULL != (ret = GNUNET_FS_uri_parse ("gnunet://fs/ksk/++", &emsg))) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } GNUNET_free (emsg); ret = GNUNET_FS_uri_parse ("gnunet://fs/ksk/foo+bar", &emsg); if (NULL == ret) { GNUNET_free (emsg); GNUNET_assert (0); } if (! GNUNET_FS_uri_test_ksk (ret)) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } if ((2 != ret->data.ksk.keywordCount) || (0 != strcmp (" foo", ret->data.ksk.keywords[0])) || (0 != strcmp (" bar", ret->data.ksk.keywords[1]))) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } uri = GNUNET_FS_uri_to_string (ret); if (0 != strcmp (uri, "gnunet://fs/ksk/foo+bar")) { GNUNET_free (uri); GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } GNUNET_free (uri); GNUNET_FS_uri_destroy (ret); return 0; }
/** * Stop probe activity. Must ONLY be used on values * returned from #GNUNET_FS_probe. * * @param sr search result to stop probing for (freed) * @return the value of the 'client_info' pointer */ void * GNUNET_FS_probe_stop (struct GNUNET_FS_SearchResult *sr) { void *client_info; GNUNET_assert (NULL == sr->sc); GNUNET_FS_search_stop_probe_ (sr); GNUNET_FS_uri_destroy (sr->uri); GNUNET_CONTAINER_meta_data_destroy (sr->meta); client_info = sr->client_info; GNUNET_free (sr); return client_info; }
static void run (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, struct GNUNET_TESTING_Peer *peer) { const char *keywords[] = { "down_foo", "down_bar" }; char *buf; struct GNUNET_CONTAINER_MetaData *meta; struct GNUNET_FS_Uri *kuri; struct GNUNET_FS_BlockOptions bo; struct GNUNET_FS_FileInformation *fi; size_t i; size_t j; fs = GNUNET_FS_start (cfg, "test-fs-search", &progress_cb, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); GNUNET_assert (NULL != fs); processed_files = 0; for(j = 0; j < NUM_FILES; j++){ buf = GNUNET_malloc (FILESIZE); for (i = 0; i < FILESIZE; i++) buf[i] = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 256); meta = GNUNET_CONTAINER_meta_data_create (); kuri = GNUNET_FS_uri_ksk_create_from_args (2, keywords); bo.content_priority = 42; bo.anonymity_level = 1; bo.replication_level = 0; bo.expiration_time = GNUNET_TIME_relative_to_absolute (LIFETIME); fi = GNUNET_FS_file_information_create_from_data (fs, "publish-context", FILESIZE, buf, kuri, meta, GNUNET_NO, &bo); GNUNET_FS_uri_destroy (kuri); GNUNET_CONTAINER_meta_data_destroy (meta); GNUNET_assert (NULL != fi); start = GNUNET_TIME_absolute_get (); publish = GNUNET_FS_publish_start (fs, fi, NULL, NULL, NULL, GNUNET_FS_PUBLISH_OPTION_NONE); GNUNET_assert (publish != NULL); } timeout_task = GNUNET_SCHEDULER_add_delayed (LIFETIME, &abort_error, NULL); }
static void run (void *cls, const struct GNUNET_CONFIGURATION_Handle *c, struct GNUNET_TESTING_Peer *peer) { const char *keywords[] = { "down_foo", "down_bar", }; char *buf; struct GNUNET_CONTAINER_MetaData *meta; struct GNUNET_FS_Uri *kuri; struct GNUNET_FS_FileInformation *fi; size_t i; struct GNUNET_FS_BlockOptions bo; cfg = c; fn = GNUNET_DISK_mktemp ("gnunet-unindex-test-dst"); fs = GNUNET_FS_start (cfg, "test-fs-unindex-persistence", &progress_cb, NULL, GNUNET_FS_FLAGS_PERSISTENCE, GNUNET_FS_OPTIONS_END); GNUNET_assert (NULL != fs); buf = GNUNET_malloc (FILESIZE); for (i = 0; i < FILESIZE; i++) buf[i] = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 256); GNUNET_assert (FILESIZE == GNUNET_DISK_fn_write (fn, buf, FILESIZE, GNUNET_DISK_PERM_USER_READ | GNUNET_DISK_PERM_USER_WRITE)); GNUNET_free (buf); meta = GNUNET_CONTAINER_meta_data_create (); kuri = GNUNET_FS_uri_ksk_create_from_args (2, keywords); bo.content_priority = 42; bo.anonymity_level = 1; bo.replication_level = 0; bo.expiration_time = GNUNET_TIME_relative_to_absolute (LIFETIME); fi = GNUNET_FS_file_information_create_from_file (fs, "publish-context", fn, kuri, meta, GNUNET_YES, &bo); GNUNET_FS_uri_destroy (kuri); GNUNET_CONTAINER_meta_data_destroy (meta); GNUNET_assert (NULL != fi); start = GNUNET_TIME_absolute_get (); publish = GNUNET_FS_publish_start (fs, fi, NULL, NULL, NULL, GNUNET_FS_PUBLISH_OPTION_NONE); GNUNET_assert (publish != NULL); }
/** * Release memory of a share item tree. * * @param toplevel toplevel of the tree to be freed */ void GNUNET_FS_share_tree_free (struct GNUNET_FS_ShareTreeItem *toplevel) { struct GNUNET_FS_ShareTreeItem *pos; while (NULL != (pos = toplevel->children_head)) GNUNET_FS_share_tree_free (pos); if (NULL != toplevel->parent) GNUNET_CONTAINER_DLL_remove (toplevel->parent->children_head, toplevel->parent->children_tail, toplevel); if (NULL != toplevel->meta) GNUNET_CONTAINER_meta_data_destroy (toplevel->meta); if (NULL != toplevel->ksk_uri) GNUNET_FS_uri_destroy (toplevel->ksk_uri); GNUNET_free_non_null (toplevel->filename); GNUNET_free_non_null (toplevel->short_filename); GNUNET_free (toplevel); }
/** * Abort the KSK publishing operation. * * @param pkc context of the operation to abort. */ void GNUNET_FS_publish_ksk_cancel (struct GNUNET_FS_PublishKskContext *pkc) { if (GNUNET_SCHEDULER_NO_TASK != pkc->ksk_task) { GNUNET_SCHEDULER_cancel (pkc->ksk_task); pkc->ksk_task = GNUNET_SCHEDULER_NO_TASK; } if (NULL != pkc->qre) { GNUNET_DATASTORE_cancel (pkc->qre); pkc->qre = NULL; } if (NULL != pkc->dsh) { GNUNET_DATASTORE_disconnect (pkc->dsh, GNUNET_NO); pkc->dsh = NULL; } GNUNET_free (pkc->cpy); GNUNET_free (pkc->kb); GNUNET_FS_uri_destroy (pkc->ksk_uri); GNUNET_free (pkc); }
static void publish_cont (void *cls, const struct GNUNET_FS_Uri *ksk_uri, const char *emsg) { char *msg; struct GNUNET_FS_Uri *sks_uri; char sbuf[1024]; char buf[1024]; char *ret; if (NULL != emsg) { FPRINTF (stderr, "Error publishing: %s\n", emsg); err = 1; GNUNET_FS_stop (fs); return; } ret = GNUNET_STRINGS_data_to_string (&nsid, sizeof (nsid), buf, sizeof (buf)); GNUNET_assert (NULL != ret); ret[0] = '\0'; GNUNET_snprintf (sbuf, sizeof (sbuf), "gnunet://fs/sks/%s/this", buf); sks_uri = GNUNET_FS_uri_parse (sbuf, &msg); if (NULL == sks_uri) { FPRINTF (stderr, "failed to parse URI `%s': %s\n", sbuf, msg); err = 1; GNUNET_FS_stop (fs); GNUNET_free_non_null (msg); return; } ksk_search = GNUNET_FS_search_start (fs, ksk_uri, 1, GNUNET_FS_SEARCH_OPTION_NONE, "ksk_search"); sks_search = GNUNET_FS_search_start (fs, sks_uri, 1, GNUNET_FS_SEARCH_OPTION_NONE, "sks_search"); GNUNET_FS_uri_destroy (sks_uri); }
/** * Iterate over all entries in a directory. Note that directories * are structured such that it is possible to iterate over the * individual blocks as well as over the entire directory. Thus * a client can call this function on the buffer in the * GNUNET_FS_ProgressCallback. Also, directories can optionally * include the contents of (small) files embedded in the directory * itself; for those files, the processor may be given the * contents of the file directly by this function. * <p> * * Note that this function maybe called on parts of directories. Thus * parser errors should not be reported _at all_ (with GNUNET_break). * Still, if some entries can be recovered despite these parsing * errors, the function should try to do this. * * @param size number of bytes in data * @param data pointer to the beginning of the directory * @param offset offset of data in the directory * @param dep function to call on each entry * @param dep_cls closure for dep * @return GNUNET_OK if this could be a block in a directory, * GNUNET_NO if this could be part of a directory (but not 100% OK) * GNUNET_SYSERR if 'data' does not represent a directory */ int GNUNET_FS_directory_list_contents (size_t size, const void *data, uint64_t offset, GNUNET_FS_DirectoryEntryProcessor dep, void *dep_cls) { struct GetFullDataClosure full_data; const char *cdata = data; char *emsg; uint64_t pos; uint64_t align; uint32_t mdSize; uint64_t epos; struct GNUNET_FS_Uri *uri; struct GNUNET_CONTAINER_MetaData *md; char *filename; if ((offset == 0) && ((size < 8 + sizeof (uint32_t)) || (0 != memcmp (cdata, GNUNET_FS_DIRECTORY_MAGIC, 8)))) return GNUNET_SYSERR; pos = offset; if (offset == 0) { GNUNET_memcpy (&mdSize, &cdata[8], sizeof (uint32_t)); mdSize = ntohl (mdSize); if (mdSize > size - 8 - sizeof (uint32_t)) { /* invalid size */ GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("MAGIC mismatch. This is not a GNUnet directory.\n")); return GNUNET_SYSERR; } md = GNUNET_CONTAINER_meta_data_deserialize (&cdata[8 + sizeof (uint32_t)], mdSize); if (md == NULL) { GNUNET_break (0); return GNUNET_SYSERR; /* malformed ! */ } dep (dep_cls, NULL, NULL, md, 0, NULL); GNUNET_CONTAINER_meta_data_destroy (md); pos = 8 + sizeof (uint32_t) + mdSize; } while (pos < size) { /* find end of URI */ if (cdata[pos] == '\0') { /* URI is never empty, must be end of block, * skip to next alignment */ align = ((pos / DBLOCK_SIZE) + 1) * DBLOCK_SIZE; if (align == pos) { /* if we were already aligned, still skip a block! */ align += DBLOCK_SIZE; } pos = align; if (pos >= size) { /* malformed - or partial download... */ break; } } epos = pos; while ((epos < size) && (cdata[epos] != '\0')) epos++; if (epos >= size) return GNUNET_NO; /* malformed - or partial download */ uri = GNUNET_FS_uri_parse (&cdata[pos], &emsg); pos = epos + 1; if (uri == NULL) { GNUNET_free (emsg); pos--; /* go back to '\0' to force going to next alignment */ continue; } if (GNUNET_FS_uri_test_ksk (uri)) { GNUNET_FS_uri_destroy (uri); GNUNET_break (0); return GNUNET_NO; /* illegal in directory! */ } GNUNET_memcpy (&mdSize, &cdata[pos], sizeof (uint32_t)); mdSize = ntohl (mdSize); pos += sizeof (uint32_t); if (pos + mdSize > size) { GNUNET_FS_uri_destroy (uri); return GNUNET_NO; /* malformed - or partial download */ } md = GNUNET_CONTAINER_meta_data_deserialize (&cdata[pos], mdSize); if (md == NULL) { GNUNET_FS_uri_destroy (uri); GNUNET_break (0); return GNUNET_NO; /* malformed ! */ } pos += mdSize; filename = GNUNET_CONTAINER_meta_data_get_by_type (md, EXTRACTOR_METATYPE_GNUNET_ORIGINAL_FILENAME); full_data.size = 0; full_data.data = NULL; GNUNET_CONTAINER_meta_data_iterate (md, &find_full_data, &full_data); if (dep != NULL) { dep (dep_cls, filename, uri, md, full_data.size, full_data.data); } GNUNET_free_non_null (full_data.data); GNUNET_free_non_null (filename); GNUNET_CONTAINER_meta_data_destroy (md); GNUNET_FS_uri_destroy (uri); } return GNUNET_OK; }
static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *c) { const char *keywords[] = { "down_foo", "down_bar", }; char *buf; struct GNUNET_CONTAINER_MetaData *meta; struct GNUNET_FS_Uri *kuri; struct GNUNET_FS_FileInformation *fi1; struct GNUNET_FS_FileInformation *fi2; struct GNUNET_FS_FileInformation *fidir; size_t i; struct GNUNET_FS_BlockOptions bo; cfg = c; setup_peer (&p1, "test_fs_publish_data.conf"); fs = GNUNET_FS_start (cfg, "test-fs-publish-persistence", &progress_cb, NULL, GNUNET_FS_FLAGS_PERSISTENCE, GNUNET_FS_OPTIONS_END); GNUNET_assert (NULL != fs); fn1 = GNUNET_DISK_mktemp ("gnunet-publish-test-dst"); buf = GNUNET_malloc (FILESIZE); for (i = 0; i < FILESIZE; i++) buf[i] = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 256); GNUNET_assert (FILESIZE == GNUNET_DISK_fn_write (fn1, buf, FILESIZE, GNUNET_DISK_PERM_USER_READ | GNUNET_DISK_PERM_USER_WRITE)); GNUNET_free (buf); fn2 = GNUNET_DISK_mktemp ("gnunet-publish-test-dst"); buf = GNUNET_malloc (FILESIZE); for (i = 0; i < FILESIZE; i++) buf[i] = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 256); GNUNET_assert (FILESIZE == GNUNET_DISK_fn_write (fn2, buf, FILESIZE, GNUNET_DISK_PERM_USER_READ | GNUNET_DISK_PERM_USER_WRITE)); GNUNET_free (buf); meta = GNUNET_CONTAINER_meta_data_create (); kuri = GNUNET_FS_uri_ksk_create_from_args (2, keywords); bo.content_priority = 42; bo.anonymity_level = 1; bo.replication_level = 0; bo.expiration_time = GNUNET_TIME_relative_to_absolute (LIFETIME); fi1 = GNUNET_FS_file_information_create_from_file (fs, "publish-context1", fn1, kuri, meta, GNUNET_YES, &bo); GNUNET_assert (NULL != fi1); bo.anonymity_level = 2; fi2 = GNUNET_FS_file_information_create_from_file (fs, "publish-context2", fn2, kuri, meta, GNUNET_YES, &bo); GNUNET_assert (NULL != fi2); bo.anonymity_level = 3; fidir = GNUNET_FS_file_information_create_empty_directory (fs, "publish-context-dir", kuri, meta, &bo, NULL); GNUNET_assert (GNUNET_OK == GNUNET_FS_file_information_add (fidir, fi1)); GNUNET_assert (GNUNET_OK == GNUNET_FS_file_information_add (fidir, fi2)); GNUNET_FS_uri_destroy (kuri); GNUNET_CONTAINER_meta_data_destroy (meta); GNUNET_assert (NULL != fidir); start = GNUNET_TIME_absolute_get (); GNUNET_FS_publish_start (fs, fidir, NULL, NULL, NULL, GNUNET_FS_PUBLISH_OPTION_NONE); GNUNET_assert (publish != NULL); }
/** * Main function that will be run by the scheduler. * * @param cls closure * @param args remaining command-line arguments * @param cfgfile name of the configuration file used (for saving, can be NULL!) * @param c configuration */ static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *c) { struct GNUNET_FS_Uri *uri; char *emsg; enum GNUNET_FS_DownloadOptions options; if (NULL == args[0]) { FPRINTF (stderr, "%s", _("You need to specify a URI argument.\n")); return; } uri = GNUNET_FS_uri_parse (args[0], &emsg); if (NULL == uri) { FPRINTF (stderr, _("Failed to parse URI: %s\n"), emsg); GNUNET_free (emsg); ret = 1; return; } if ((!GNUNET_FS_uri_test_chk (uri)) && (!GNUNET_FS_uri_test_loc (uri))) { FPRINTF (stderr, "%s", _("Only CHK or LOC URIs supported.\n")); ret = 1; GNUNET_FS_uri_destroy (uri); return; } if (NULL == filename) { FPRINTF (stderr, "%s", _("Target filename must be specified.\n")); ret = 1; GNUNET_FS_uri_destroy (uri); return; } cfg = c; ctx = GNUNET_FS_start (cfg, "gnunet-download", &progress_cb, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_DOWNLOAD_PARALLELISM, parallelism, GNUNET_FS_OPTIONS_REQUEST_PARALLELISM, request_parallelism, GNUNET_FS_OPTIONS_END); if (NULL == ctx) { FPRINTF (stderr, _("Could not initialize `%s' subsystem.\n"), "FS"); GNUNET_FS_uri_destroy (uri); ret = 1; return; } options = GNUNET_FS_DOWNLOAD_OPTION_NONE; if (do_recursive) options |= GNUNET_FS_DOWNLOAD_OPTION_RECURSIVE; if (local_only) options |= GNUNET_FS_DOWNLOAD_OPTION_LOOPBACK_ONLY; dc = GNUNET_FS_download_start (ctx, uri, NULL, filename, NULL, 0, GNUNET_FS_uri_chk_get_file_size (uri), anonymity, options, NULL, NULL); GNUNET_FS_uri_destroy (uri); if (dc == NULL) { GNUNET_FS_stop (ctx); ctx = NULL; return; } GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &shutdown_task, NULL); }
static void run (void *cls, char *const *args, const char *cfgfile, const struct GNUNET_CONFIGURATION_Handle *cfg) { const char *keywords[] = { "down_foo", "down_bar", }; char *fn1; char *fn2; char *buf; struct GNUNET_CONTAINER_MetaData *meta; struct GNUNET_FS_Uri *kuri; struct GNUNET_FS_FileInformation *fi1; struct GNUNET_FS_FileInformation *fi2; struct GNUNET_FS_FileInformation *fidir; struct GNUNET_FS_Handle *fs; size_t i; struct GNUNET_FS_BlockOptions bo; fs = GNUNET_FS_start (cfg, "test-fs-file-information", NULL, NULL, GNUNET_FS_FLAGS_NONE, GNUNET_FS_OPTIONS_END); fn1 = GNUNET_DISK_mktemp ("gnunet-file_information-test-dst"); buf = GNUNET_malloc (FILESIZE); for (i = 0; i < FILESIZE; i++) buf[i] = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 256); GNUNET_assert (FILESIZE == GNUNET_DISK_fn_write (fn1, buf, FILESIZE, GNUNET_DISK_PERM_USER_READ | GNUNET_DISK_PERM_USER_WRITE)); GNUNET_free (buf); fn2 = GNUNET_DISK_mktemp ("gnunet-file_information-test-dst"); buf = GNUNET_malloc (FILESIZE); for (i = 0; i < FILESIZE; i++) buf[i] = GNUNET_CRYPTO_random_u32 (GNUNET_CRYPTO_QUALITY_WEAK, 256); GNUNET_assert (FILESIZE == GNUNET_DISK_fn_write (fn2, buf, FILESIZE, GNUNET_DISK_PERM_USER_READ | GNUNET_DISK_PERM_USER_WRITE)); GNUNET_free (buf); meta = GNUNET_CONTAINER_meta_data_create (); kuri = GNUNET_FS_uri_ksk_create_from_args (2, keywords); bo.content_priority = 42; bo.anonymity_level = 1; bo.replication_level = 0; bo.expiration_time = GNUNET_TIME_relative_to_absolute (LIFETIME); fi1 = GNUNET_FS_file_information_create_from_file (fs, "file_information-context1", fn1, kuri, meta, GNUNET_YES, &bo); GNUNET_assert (fi1 != NULL); fi2 = GNUNET_FS_file_information_create_from_file (fs, "file_information-context2", fn2, kuri, meta, GNUNET_YES, &bo); GNUNET_assert (fi2 != NULL); fidir = GNUNET_FS_file_information_create_empty_directory (fs, "file_information-context-dir", kuri, meta, &bo, NULL); GNUNET_assert (GNUNET_OK == GNUNET_FS_file_information_add (fidir, fi1)); GNUNET_assert (GNUNET_OK == GNUNET_FS_file_information_add (fidir, fi2)); GNUNET_FS_uri_destroy (kuri); GNUNET_CONTAINER_meta_data_destroy (meta); GNUNET_assert (NULL != fidir); /* FIXME: test more of API! */ GNUNET_FS_file_information_destroy (fidir, &mycleaner, NULL); GNUNET_DISK_directory_remove (fn1); GNUNET_DISK_directory_remove (fn2); GNUNET_free_non_null (fn1); GNUNET_free_non_null (fn2); GNUNET_FS_stop (fs); }
static void * progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) { const char *keywords[] = { "down_foo" }; struct GNUNET_FS_Uri *kuri; switch (event->status) { case GNUNET_FS_STATUS_PUBLISH_PROGRESS: GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Publish is progressing (%llu/%llu at level %u off %llu)...\n", (unsigned long long) event->value.publish.completed, (unsigned long long) event->value.publish.size, event->value.publish.specifics.progress.depth, (unsigned long long) event->value.publish.specifics. progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_COMPLETED: kuri = GNUNET_FS_uri_ksk_create_from_args (1, keywords); start = GNUNET_TIME_absolute_get (); GNUNET_FS_search_start (fs, kuri, 1, GNUNET_FS_SEARCH_OPTION_NONE, "search"); GNUNET_FS_uri_destroy (kuri); GNUNET_assert (search != NULL); break; case GNUNET_FS_STATUS_PUBLISH_SUSPEND: if (event->value.publish.pc == publish) publish = NULL; break; case GNUNET_FS_STATUS_PUBLISH_RESUME: if (NULL == publish) publish = event->value.publish.pc; break; case GNUNET_FS_STATUS_SEARCH_RESULT: /* FIXME: consider_restart (event->status); cannot be tested with * search result since we exit here after the first one... */ GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Search complete.\n"); GNUNET_SCHEDULER_add_continuation (&abort_search_task, NULL, GNUNET_SCHEDULER_REASON_PREREQ_DONE); break; case GNUNET_FS_STATUS_PUBLISH_ERROR: FPRINTF (stderr, "Error publishing file: %s\n", event->value.publish.specifics.error.message); GNUNET_break (0); GNUNET_SCHEDULER_add_continuation (&abort_publish_task, NULL, GNUNET_SCHEDULER_REASON_PREREQ_DONE); break; case GNUNET_FS_STATUS_SEARCH_ERROR: FPRINTF (stderr, "Error searching file: %s\n", event->value.search.specifics.error.message); GNUNET_SCHEDULER_add_continuation (&abort_search_task, NULL, GNUNET_SCHEDULER_REASON_PREREQ_DONE); break; case GNUNET_FS_STATUS_SEARCH_SUSPEND: if (event->value.search.sc == search) search = NULL; break; case GNUNET_FS_STATUS_SEARCH_RESUME: if (NULL == search) { search = event->value.search.sc; return "search"; } break; case GNUNET_FS_STATUS_PUBLISH_START: GNUNET_assert (0 == strcmp ("publish-context", event->value.publish.cctx)); GNUNET_assert (NULL == event->value.publish.pctx); GNUNET_assert (FILESIZE == event->value.publish.size); GNUNET_assert (0 == event->value.publish.completed); GNUNET_assert (1 == event->value.publish.anonymity); break; case GNUNET_FS_STATUS_PUBLISH_STOPPED: GNUNET_assert (publish == event->value.publish.pc); GNUNET_assert (FILESIZE == event->value.publish.size); GNUNET_assert (1 == event->value.publish.anonymity); GNUNET_FS_stop (fs); fs = NULL; break; case GNUNET_FS_STATUS_SEARCH_START: consider_restart (event->status); GNUNET_assert (search == NULL); search = event->value.search.sc; GNUNET_assert (0 == strcmp ("search", event->value.search.cctx)); GNUNET_assert (1 == event->value.search.anonymity); break; case GNUNET_FS_STATUS_SEARCH_RESULT_STOPPED: break; case GNUNET_FS_STATUS_SEARCH_STOPPED: GNUNET_assert (search == event->value.search.sc); GNUNET_SCHEDULER_add_continuation (&abort_publish_task, NULL, GNUNET_SCHEDULER_REASON_PREREQ_DONE); search = NULL; break; default: FPRINTF (stderr, "Unexpected event: %d\n", event->status); break; } return NULL; }
static int testLocation () { struct GNUNET_FS_Uri *uri; char *uric; struct GNUNET_FS_Uri *uri2; struct GNUNET_FS_Uri *baseURI; char *emsg; struct GNUNET_CRYPTO_EddsaPrivateKey *pk; baseURI = GNUNET_FS_uri_parse ("gnunet://fs/chk/4QZP479A9SKGFNMQ2ZBCYE71YV2QMTVGWTVPB6A10ASVCKXDHB05DKPSC7ZF6E9P9W1VE47394EQY7NXA47Q6R35M7P1MJPGP59D1Z8.D54QD1K5XCG5878T6YZ19AM60MQ6FC0YNVK7QY08KK0KM0FJJ3KQWYG112FN5T07KN7J0X35DF6WVBT9B8ZMZ3X2BXJ22X3KFQ6MV2G.15999", &emsg); GNUNET_assert (baseURI != NULL); GNUNET_assert (emsg == NULL); pk = GNUNET_CRYPTO_eddsa_key_create (); uri = GNUNET_FS_uri_loc_create (baseURI, pk, GNUNET_TIME_absolute_get ()); GNUNET_free (pk); if (NULL == uri) { GNUNET_break (0); GNUNET_FS_uri_destroy (baseURI); return 1; } if (! GNUNET_FS_uri_test_loc (uri)) { GNUNET_break (0); GNUNET_FS_uri_destroy (uri); GNUNET_FS_uri_destroy (baseURI); return 1; } uri2 = GNUNET_FS_uri_loc_get_uri (uri); if (! GNUNET_FS_uri_test_equal (baseURI, uri2)) { GNUNET_break (0); GNUNET_FS_uri_destroy (uri); GNUNET_FS_uri_destroy (uri2); GNUNET_FS_uri_destroy (baseURI); return 1; } GNUNET_FS_uri_destroy (uri2); GNUNET_FS_uri_destroy (baseURI); uric = GNUNET_FS_uri_to_string (uri); #if 0 /* not for the faint of heart: */ printf ("URI: `%s'\n", uric); #endif uri2 = GNUNET_FS_uri_parse (uric, &emsg); GNUNET_free (uric); if (uri2 == NULL) { fprintf (stderr, "URI parsing failed: %s\n", emsg); GNUNET_break (0); GNUNET_FS_uri_destroy (uri); GNUNET_free (emsg); return 1; } GNUNET_assert (NULL == emsg); if (GNUNET_YES != GNUNET_FS_uri_test_equal (uri, uri2)) { GNUNET_break (0); GNUNET_FS_uri_destroy (uri); GNUNET_FS_uri_destroy (uri2); return 1; } GNUNET_FS_uri_destroy (uri2); GNUNET_FS_uri_destroy (uri); return 0; }
/** * Clean up after completion of an unindex operation. * * @param uc handle */ void GNUNET_FS_unindex_stop (struct GNUNET_FS_UnindexContext *uc) { struct GNUNET_FS_ProgressInfo pi; if (uc->dscan != NULL) { GNUNET_FS_directory_scan_abort (uc->dscan); uc->dscan = NULL; } if (NULL != uc->dqe) { GNUNET_DATASTORE_cancel (uc->dqe); uc->dqe = NULL; } if (uc->fhc != NULL) { GNUNET_CRYPTO_hash_file_cancel (uc->fhc); uc->fhc = NULL; } if (uc->client != NULL) { GNUNET_CLIENT_disconnect (uc->client); uc->client = NULL; } if (NULL != uc->dsh) { GNUNET_DATASTORE_disconnect (uc->dsh, GNUNET_NO); uc->dsh = NULL; } if (NULL != uc->ksk_uri) { GNUNET_FS_uri_destroy (uc->ksk_uri); uc->ksk_uri = NULL; } if (NULL != uc->tc) { GNUNET_FS_tree_encoder_finish (uc->tc, NULL); uc->tc = NULL; } if (uc->fh != NULL) { GNUNET_DISK_file_close (uc->fh); uc->fh = NULL; } GNUNET_FS_end_top (uc->h, uc->top); if (uc->serialization != NULL) { GNUNET_FS_remove_sync_file_ (uc->h, GNUNET_FS_SYNC_PATH_MASTER_UNINDEX, uc->serialization); GNUNET_free (uc->serialization); uc->serialization = NULL; } pi.status = GNUNET_FS_STATUS_UNINDEX_STOPPED; pi.value.unindex.eta = GNUNET_TIME_UNIT_ZERO; GNUNET_FS_unindex_make_status_ (&pi, uc, (uc->state == UNINDEX_STATE_COMPLETE) ? uc->file_size : 0); GNUNET_break (NULL == uc->client_info); GNUNET_free_non_null (uc->emsg); GNUNET_free (uc->filename); GNUNET_free (uc); }
static int testFile (int i) { char *uri; struct GNUNET_FS_Uri *ret; char *emsg; if (NULL != (ret = GNUNET_FS_uri_parse ("gnunet://fs/chk/C282GG70GKK41O4551011DO413KFBVTVMQG1OG30I0K4045N0G41HAPB82G680A02JRVVFO8URVRU2F159011DO41000000022RG820.RNVVVVOOLCLK065B5D04HTNVNSIB2AI022RG8200HSLK1CO1000ATQ98824DMA2032LIMG50CG0K057NVUVG200000H00000440000.42", &emsg))) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } GNUNET_free (emsg); if (NULL != (ret = GNUNET_FS_uri_parse ("gnunet://fs/chk/C282GG70GKK41O4551011DO413KFBVTVMQG1OG30I0K4045N0G41HAPB82G680A02JRVVFO8URVRU2F159011DO41000000022RG820.RNVVVVOOLCLK065B5D04HTNVNSIB2AI022RG8200HSLK1CO1000ATQ98824DMA2032LIMG50CG0K057NVUVG200000H000004400000", &emsg))) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } GNUNET_free (emsg); if (NULL != (ret = GNUNET_FS_uri_parse ("gnunet://fs/chk/C282GG70GKK41O4551011DO413KFBVTVMQG1OG30I0K4045N0G41HAPB82G680A02JRVVFO8URVRU2F159011DO41000000022RG820.RNVVVVOOLCLK065B5D04HTNVNSIB2AI022RG8200HSLK1CO1000ATQ98824DMA2032LIMG50CG0K057NVUVG200000H000004400000.FGH", &emsg))) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } GNUNET_free (emsg); ret = GNUNET_FS_uri_parse ("gnunet://fs/chk/4QZP479A9SKGFNMQ2ZBCYE71YV2QMTVGWTVPB6A10ASVCKXDHB05DKPSC7ZF6E9P9W1VE47394EQY7NXA47Q6R35M7P1MJPGP59D1Z8.D54QD1K5XCG5878T6YZ19AM60MQ6FC0YNVK7QY08KK0KM0FJJ3KQWYG112FN5T07KN7J0X35DF6WVBT9B8ZMZ3X2BXJ22X3KFQ6MV2G.42", &emsg); if (ret == NULL) { GNUNET_free (emsg); GNUNET_assert (0); } if (GNUNET_FS_uri_test_ksk (ret)) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } if (GNUNET_FS_uri_test_sks (ret)) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } if (GNUNET_ntohll (ret->data.chk.file_length) != 42) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } uri = GNUNET_FS_uri_to_string (ret); if (0 != strcmp (uri, "gnunet://fs/chk/4QZP479A9SKGFNMQ2ZBCYE71YV2QMTVGWTVPB6A10ASVCKXDHB05DKPSC7ZF6E9P9W1VE47394EQY7NXA47Q6R35M7P1MJPGP59D1Z8.D54QD1K5XCG5878T6YZ19AM60MQ6FC0YNVK7QY08KK0KM0FJJ3KQWYG112FN5T07KN7J0X35DF6WVBT9B8ZMZ3X2BXJ22X3KFQ6MV2G.42")) { GNUNET_free (uri); GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } GNUNET_free (uri); GNUNET_FS_uri_destroy (ret); return 0; }
static int testNamespace (int i) { char *uri; struct GNUNET_FS_Uri *ret; char *emsg; struct GNUNET_CRYPTO_EcdsaPrivateKey *ph; struct GNUNET_CRYPTO_EcdsaPublicKey id; char buf[1024]; char ubuf[1024]; char *sret; if (NULL != (ret = GNUNET_FS_uri_parse ("gnunet://fs/sks/D1KJS9H2A82Q65VKQ0ML3RFU6U1D3VUK", &emsg))) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } GNUNET_free (emsg); if (NULL != (ret = GNUNET_FS_uri_parse ("gnunet://fs/sks/XQHH4R288W26EBV369F6RCE0PJVJTX2Y74Q2FJPMPGA31HJX2JG/this", &emsg))) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } GNUNET_free (emsg); if (NULL != (ret = GNUNET_FS_uri_parse ("gnunet://fs/sks/test", &emsg))) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } GNUNET_free (emsg); ph = GNUNET_CRYPTO_ecdsa_key_create (); GNUNET_CRYPTO_ecdsa_key_get_public (ph, &id); sret = GNUNET_STRINGS_data_to_string (&id, sizeof (id), ubuf, sizeof (ubuf) - 1); GNUNET_assert (NULL != sret); sret[0] = '\0'; GNUNET_snprintf (buf, sizeof (buf), "gnunet://fs/sks/%s/test", ubuf); ret = GNUNET_FS_uri_parse (buf, &emsg); if (NULL == ret) { GNUNET_free (emsg); GNUNET_assert (0); } if (GNUNET_FS_uri_test_ksk (ret)) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } if (!GNUNET_FS_uri_test_sks (ret)) { GNUNET_FS_uri_destroy (ret); GNUNET_assert (0); } uri = GNUNET_FS_uri_to_string (ret); if (0 != strcmp (uri, buf)) { GNUNET_FS_uri_destroy (ret); GNUNET_free (uri); GNUNET_assert (0); } GNUNET_free (uri); GNUNET_FS_uri_destroy (ret); return 0; }
/** * Add an entry to a directory. * * @param bld directory to extend * @param uri uri of the entry (must not be a KSK) * @param md metadata of the entry * @param data raw data of the entry, can be NULL, otherwise * data must point to exactly the number of bytes specified * by the uri which must be of type LOC or CHK */ void GNUNET_FS_directory_builder_add (struct GNUNET_FS_DirectoryBuilder *bld, const struct GNUNET_FS_Uri *uri, const struct GNUNET_CONTAINER_MetaData *md, const void *data) { struct GNUNET_FS_Uri *curi; struct BuilderEntry *e; uint64_t fsize; uint32_t big; ssize_t ret; size_t mds; size_t mdxs; char *uris; char *ser; char *sptr; size_t slen; struct GNUNET_CONTAINER_MetaData *meta; const struct GNUNET_CONTAINER_MetaData *meta_use; GNUNET_assert (!GNUNET_FS_uri_test_ksk (uri)); if (NULL != data) { GNUNET_assert (!GNUNET_FS_uri_test_sks (uri)); if (GNUNET_FS_uri_test_chk (uri)) { fsize = GNUNET_FS_uri_chk_get_file_size (uri); } else { curi = GNUNET_FS_uri_loc_get_uri (uri); GNUNET_assert (NULL != curi); fsize = GNUNET_FS_uri_chk_get_file_size (curi); GNUNET_FS_uri_destroy (curi); } } else { fsize = 0; /* not given */ } if (fsize > MAX_INLINE_SIZE) fsize = 0; /* too large */ uris = GNUNET_FS_uri_to_string (uri); slen = strlen (uris) + 1; mds = GNUNET_CONTAINER_meta_data_get_serialized_size (md); meta_use = md; meta = NULL; if (fsize > 0) { meta = GNUNET_CONTAINER_meta_data_duplicate (md); GNUNET_CONTAINER_meta_data_insert (meta, "<gnunet>", EXTRACTOR_METATYPE_GNUNET_FULL_DATA, EXTRACTOR_METAFORMAT_BINARY, NULL, data, fsize); mdxs = GNUNET_CONTAINER_meta_data_get_serialized_size (meta); if ((slen + sizeof (uint32_t) + mdxs - 1) / DBLOCK_SIZE == (slen + sizeof (uint32_t) + mds - 1) / DBLOCK_SIZE) { /* adding full data would not cause us to cross * additional blocks, so add it! */ meta_use = meta; mds = mdxs; } } if (mds > GNUNET_MAX_MALLOC_CHECKED / 2) mds = GNUNET_MAX_MALLOC_CHECKED / 2; e = GNUNET_malloc (sizeof (struct BuilderEntry) + slen + mds + sizeof (uint32_t)); ser = (char *) &e[1]; memcpy (ser, uris, slen); GNUNET_free (uris); sptr = &ser[slen + sizeof (uint32_t)]; ret = GNUNET_CONTAINER_meta_data_serialize (meta_use, &sptr, mds, GNUNET_CONTAINER_META_DATA_SERIALIZE_PART); if (NULL != meta) GNUNET_CONTAINER_meta_data_destroy (meta); if (ret == -1) mds = 0; else mds = ret; big = htonl (mds); memcpy (&ser[slen], &big, sizeof (uint32_t)); e->len = slen + sizeof (uint32_t) + mds; e->next = bld->head; bld->head = e; bld->count++; }
/** * Function called from datastore with result from us looking for * a UBlock. There are four cases: * 1) no result, means we move on to the next keyword * 2) UID is the same as the first UID, means we move on to next keyword * 3) UBlock for a different CHK, means we keep looking for more * 4) UBlock is for our CHK, means we remove the block and then move * on to the next keyword * * @param cls the 'struct GNUNET_FS_UnindexContext *' * @param key key for the content * @param size number of bytes in data * @param data content stored * @param type type of the content * @param priority priority of the content * @param anonymity anonymity-level for the content * @param expiration expiration time for the content * @param uid unique identifier for the datum; * maybe 0 if no unique identifier is available */ static void process_kblock_for_unindex (void *cls, const struct GNUNET_HashCode *key, size_t size, const void *data, enum GNUNET_BLOCK_Type type, uint32_t priority, uint32_t anonymity, struct GNUNET_TIME_Absolute expiration, uint64_t uid) { struct GNUNET_FS_UnindexContext *uc = cls; const struct UBlock *ub; struct GNUNET_FS_Uri *chk_uri; struct GNUNET_HashCode query; struct GNUNET_HashCode dh; uc->dqe = NULL; if (NULL == data) { /* no result */ GNUNET_CONTAINER_multihashmap_clear (uc->seen_dh); uc->ksk_offset++; GNUNET_FS_unindex_do_remove_kblocks_ (uc); return; } GNUNET_CRYPTO_hash (data, size, &dh); if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_contains (uc->seen_dh, &dh)) { GNUNET_CONTAINER_multihashmap_clear (uc->seen_dh); uc->ksk_offset++; GNUNET_FS_unindex_do_remove_kblocks_ (uc); return; } GNUNET_assert (GNUNET_OK == GNUNET_CONTAINER_multihashmap_put (uc->seen_dh, &dh, uc, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); GNUNET_assert (GNUNET_BLOCK_TYPE_FS_UBLOCK == type); if (size < sizeof (struct UBlock)) { GNUNET_break (0); goto get_next; } ub = data; GNUNET_CRYPTO_hash (&ub->verification_key, sizeof (ub->verification_key), &query); if (0 != memcmp (&query, key, sizeof (struct GNUNET_HashCode))) { /* result does not match our keyword, skip */ goto get_next; } { char pt[size - sizeof (struct UBlock)]; struct GNUNET_CRYPTO_EcdsaPublicKey anon_pub; const char *keyword; GNUNET_CRYPTO_ecdsa_key_get_public (GNUNET_CRYPTO_ecdsa_key_get_anonymous (), &anon_pub); keyword = &uc->ksk_uri->data.ksk.keywords[uc->ksk_offset][1]; GNUNET_FS_ublock_decrypt_ (&ub[1], size - sizeof (struct UBlock), &anon_pub, keyword, pt); if (NULL == memchr (&pt[1], 0, sizeof (pt) - 1)) { GNUNET_break_op (0); /* malformed UBlock */ goto get_next; } chk_uri = GNUNET_FS_uri_parse (&pt[1], NULL); if (NULL == chk_uri) { GNUNET_break_op (0); /* malformed UBlock */ goto get_next; } } if (0 != memcmp (&uc->chk, &chk_uri->data.chk.chk, sizeof (struct ContentHashKey))) { /* different CHK, ignore */ GNUNET_FS_uri_destroy (chk_uri); goto get_next; } GNUNET_FS_uri_destroy (chk_uri); /* matches! */ uc->dqe = GNUNET_DATASTORE_remove (uc->dsh, key, size, data, 0 /* priority */, 1 /* queue size */, GNUNET_TIME_UNIT_FOREVER_REL, &continue_after_remove, uc); return; get_next: uc->dqe = GNUNET_DATASTORE_get_key (uc->dsh, uc->roff++, &uc->uquery, GNUNET_BLOCK_TYPE_FS_UBLOCK, 0 /* priority */, 1 /* queue size */, GNUNET_TIME_UNIT_FOREVER_REL, &process_kblock_for_unindex, uc); }
static void * progress_cb (void *cls, const struct GNUNET_FS_ProgressInfo *event) { struct GNUNET_FS_Uri *kuri; switch (event->status) { case GNUNET_FS_STATUS_PUBLISH_PROGRESS: GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Publish is progressing (%llu/%llu at level %u off %llu)...\n", (unsigned long long) event->value.publish.completed, (unsigned long long) event->value.publish.size, event->value.publish.specifics.progress.depth, (unsigned long long) event->value.publish.specifics. progress.offset); break; case GNUNET_FS_STATUS_PUBLISH_PROGRESS_DIRECTORY: break; case GNUNET_FS_STATUS_PUBLISH_COMPLETED: processed_files++; if(processed_files == NUM_FILES) { char *emsg = NULL; kuri = GNUNET_FS_uri_ksk_create ("+down_foo +down_bar", &emsg); GNUNET_assert (kuri != NULL); start = GNUNET_TIME_absolute_get (); search = GNUNET_FS_search_start (fs, kuri, 1, GNUNET_FS_SEARCH_OPTION_NONE, "search"); GNUNET_FS_uri_destroy (kuri); GNUNET_assert (search != NULL); } break; case GNUNET_FS_STATUS_SEARCH_RESULT: GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Search complete.\n"); GNUNET_SCHEDULER_add_now (&abort_search_task, NULL); break; case GNUNET_FS_STATUS_PUBLISH_ERROR: FPRINTF (stderr, "Error publishing file: %s\n", event->value.publish.specifics.error.message); GNUNET_break (0); GNUNET_SCHEDULER_add_now (&abort_publish_task, NULL); break; case GNUNET_FS_STATUS_SEARCH_ERROR: FPRINTF (stderr, "Error searching file: %s\n", event->value.search.specifics.error.message); GNUNET_SCHEDULER_add_now (&abort_search_task, NULL); break; case GNUNET_FS_STATUS_PUBLISH_START: GNUNET_assert (0 == strcmp ("publish-context", event->value.publish.cctx)); GNUNET_assert (NULL == event->value.publish.pctx); GNUNET_assert (FILESIZE == event->value.publish.size); GNUNET_assert (0 == event->value.publish.completed); GNUNET_assert (1 == event->value.publish.anonymity); break; case GNUNET_FS_STATUS_PUBLISH_STOPPED: GNUNET_assert (publish == event->value.publish.pc); GNUNET_assert (FILESIZE == event->value.publish.size); GNUNET_assert (1 == event->value.publish.anonymity); GNUNET_FS_stop (fs); fs = NULL; break; case GNUNET_FS_STATUS_SEARCH_START: GNUNET_assert (search == NULL); GNUNET_assert (0 == strcmp ("search", event->value.search.cctx)); GNUNET_assert (1 == event->value.search.anonymity); break; case GNUNET_FS_STATUS_SEARCH_RESULT_STOPPED: break; case GNUNET_FS_STATUS_SEARCH_STOPPED: GNUNET_assert (search == event->value.search.sc); GNUNET_SCHEDULER_add_now (&abort_publish_task, NULL); break; default: FPRINTF (stderr, "Unexpected event: %d\n", event->status); break; } return NULL; }
static int testDirectory (unsigned int i) { struct GNUNET_FS_DirectoryBuilder *db; char *data; size_t dlen; struct GNUNET_FS_Uri **uris; struct GNUNET_CONTAINER_MetaData **mds; struct GNUNET_CONTAINER_MetaData *meta; struct PCLS cls; char *emsg; int p; int q; char uri[512]; char txt[128]; int ret = 0; struct GNUNET_TIME_Absolute start; const char *s; cls.max = i; uris = GNUNET_malloc (sizeof (struct GNUNET_FS_Uri *) * i); mds = GNUNET_malloc (sizeof (struct GNUNET_CONTAINER_MetaData *) * i); meta = GNUNET_CONTAINER_meta_data_create (); GNUNET_CONTAINER_meta_data_insert (meta, "<test>", EXTRACTOR_METATYPE_TITLE, EXTRACTOR_METAFORMAT_UTF8, "text/plain", "A title", strlen ("A title") + 1); GNUNET_CONTAINER_meta_data_insert (meta, "<test>", EXTRACTOR_METATYPE_AUTHOR_NAME, EXTRACTOR_METAFORMAT_UTF8, "text/plain", "An author", strlen ("An author") + 1); for (p = 0; p < i; p++) { mds[p] = GNUNET_CONTAINER_meta_data_create (); for (q = 0; q <= p; q++) { GNUNET_snprintf (txt, sizeof (txt), "%u -- %u\n", p, q); GNUNET_CONTAINER_meta_data_insert (mds[p], "<test>", #if HAVE_EXTRACTOR_H q % EXTRACTOR_metatype_get_max (), #else q % 128, #endif EXTRACTOR_METAFORMAT_UTF8, "text/plain", txt, strlen (txt) + 1); } GNUNET_snprintf (uri, sizeof (uri), "gnunet://fs/chk/C282GG70GKK41O4551011DO413KFBVTVMQG1OG30I0K4045N0G41HAPB82G680A02JRVVFO8URVRU2F159011DO41000000022RG820.RNVVVVOOLCLK065B5D04HTNVNSIB2AI022RG8200HSLK1CO1000ATQ98824DMA2032LIMG50CG0K057NVUVG200000H000004400000.%u", p); emsg = NULL; uris[p] = GNUNET_FS_uri_parse (uri, &emsg); if (uris[p] == NULL) { GNUNET_CONTAINER_meta_data_destroy (mds[p]); while (--p > 0) { GNUNET_CONTAINER_meta_data_destroy (mds[p]); GNUNET_FS_uri_destroy (uris[p]); } GNUNET_free (mds); GNUNET_free (uris); GNUNET_free (emsg); GNUNET_CONTAINER_meta_data_destroy (meta); ABORT (); /* error in testcase */ } GNUNET_assert (emsg == NULL); } start = GNUNET_TIME_absolute_get (); db = GNUNET_FS_directory_builder_create (meta); for (p = 0; p < i; p++) GNUNET_FS_directory_builder_add (db, uris[p], mds[p], NULL); GNUNET_FS_directory_builder_finish (db, &dlen, (void **) &data); s = GNUNET_STRINGS_relative_time_to_string (GNUNET_TIME_absolute_get_duration (start), GNUNET_YES); FPRINTF (stdout, "Creating directory with %u entires and total size %llu took %s\n", i, (unsigned long long) dlen, s); if (i < 100) { cls.pos = 0; cls.uri = uris; cls.md = mds; GNUNET_FS_directory_list_contents (dlen, data, 0, &processor, &cls); GNUNET_assert (cls.pos == i); } GNUNET_free (data); GNUNET_CONTAINER_meta_data_destroy (meta); for (p = 0; p < i; p++) { GNUNET_CONTAINER_meta_data_destroy (mds[p]); GNUNET_FS_uri_destroy (uris[p]); } GNUNET_free (uris); GNUNET_free (mds); return ret; }
/** * Process a share item tree, moving frequent keywords up and * copying frequent metadata up. * * @param tc trim context with hash maps to use * @param tree tree to trim */ static void share_tree_trim (struct TrimContext *tc, struct GNUNET_FS_ShareTreeItem *tree) { struct GNUNET_FS_ShareTreeItem *pos; unsigned int num_children; /* first, trim all children */ num_children = 0; for (pos = tree->children_head; NULL != pos; pos = pos->next) { share_tree_trim (tc, pos); num_children++; } /* consider adding filename to directory meta data */ if (tree->is_directory == GNUNET_YES) { const char *user = getenv ("USER"); if ( (user == NULL) || (0 != strncasecmp (user, tree->short_filename, strlen(user)))) { /* only use filename if it doesn't match $USER */ if (NULL == tree->meta) tree->meta = GNUNET_CONTAINER_meta_data_create (); GNUNET_CONTAINER_meta_data_insert (tree->meta, "<libgnunetfs>", EXTRACTOR_METATYPE_GNUNET_ORIGINAL_FILENAME, EXTRACTOR_METAFORMAT_UTF8, "text/plain", tree->short_filename, strlen (tree->short_filename) + 1); } } if (1 >= num_children) return; /* nothing to trim */ /* now, count keywords and meta data in children */ for (pos = tree->children_head; NULL != pos; pos = pos->next) { if (NULL != pos->meta) GNUNET_CONTAINER_meta_data_iterate (pos->meta, &add_to_meta_counter, tc->metacounter); if (NULL != pos->ksk_uri) GNUNET_FS_uri_ksk_get_keywords (pos->ksk_uri, &add_to_keyword_counter, tc->keywordcounter); } /* calculate threshold for moving keywords / meta data */ tc->move_threshold = 1 + (num_children / 2); /* remove high-frequency keywords from children */ for (pos = tree->children_head; NULL != pos; pos = pos->next) { tc->pos = pos; if (NULL != pos->ksk_uri) { struct GNUNET_FS_Uri *ksk_uri_copy = GNUNET_FS_uri_dup (pos->ksk_uri); GNUNET_FS_uri_ksk_get_keywords (ksk_uri_copy, &remove_high_frequency_keywords, tc); GNUNET_FS_uri_destroy (ksk_uri_copy); } } /* add high-frequency meta data and keywords to parent */ tc->pos = tree; GNUNET_CONTAINER_multihashmap_iterate (tc->keywordcounter, &migrate_and_drop_keywords, tc); GNUNET_CONTAINER_multihashmap_iterate (tc->metacounter, &migrate_and_drop_metadata, tc); }