static void upload_stats_add(const char *pathname, filesize_t size, const char *name, guint32 attempts, guint32 complete, guint64 ul_bytes, time_t rtime, time_t dtime, const struct sha1 *sha1) { static const struct ul_stats zero_stats; struct ul_stats *s; g_assert(pathname != NULL); g_assert(name != NULL); WALLOC(s); *s = zero_stats; s->pathname = atom_str_get(pathname); s->filename = atom_str_get(name); s->size = size; s->attempts = attempts; s->complete = complete; s->norm = size > 0 ? 1.0 * ul_bytes / size : 0.0; s->bytes_sent = ul_bytes; s->rtime = rtime; s->dtime = dtime; s->sha1 = sha1 ? atom_sha1_get(sha1) : NULL; if (!upload_stats_list) { g_assert(!upload_stats_by_sha1); upload_stats_list = hash_list_new(ul_stats_hash, ul_stats_eq); upload_stats_by_sha1 = g_hash_table_new(sha1_hash, sha1_eq); } hash_list_append(upload_stats_list, s); if (s->sha1) gm_hash_table_insert_const(upload_stats_by_sha1, s->sha1, s); gcu_upload_stats_gui_add(s); }
/** * Allocate new publisher entry. */ static struct publisher_entry * publisher_entry_alloc(const sha1_t *sha1) { struct publisher_entry *pe; WALLOC0(pe); pe->magic = PUBLISHER_MAGIC; pe->sha1 = atom_sha1_get(sha1); return pe; }
void magnet_set_sha1(struct magnet_resource *res, const struct sha1 *sha1) { const struct sha1 *atom; g_return_if_fail(res); g_return_if_fail(sha1); atom = atom_sha1_get(sha1); atom_sha1_free_null(&res->sha1); res->sha1 = atom; }
/** * Add a new entry to the in-memory cache. */ static void add_volatile_cache_entry(const char *filename, filesize_t size, time_t mtime, const struct sha1 *sha1, const struct tth *tth, bool known_to_be_shared) { struct sha1_cache_entry *item; WALLOC(item); item->file_name = atom_str_get(filename); item->size = size; item->mtime = mtime; item->sha1 = atom_sha1_get(sha1); item->tth = tth ? atom_tth_get(tth) : NULL; item->shared = known_to_be_shared; hikset_insert_key(sha1_cache, &item->file_name); }
/** * Initialize the THEX download context. */ struct thex_download * thex_download_create(void *owner, gnet_host_t *host, const struct sha1 *sha1, const struct tth *tth, filesize_t filesize) { static const struct thex_download zero_ctx; struct thex_download *ctx; g_return_val_if_fail(host, NULL); g_return_val_if_fail(sha1, NULL); g_return_val_if_fail(tth, NULL); WALLOC(ctx); *ctx = zero_ctx; ctx->owner = owner; gnet_host_copy(&ctx->host, host); ctx->sha1 = atom_sha1_get(sha1); ctx->tth = atom_tth_get(tth); ctx->filesize = filesize; return ctx; }
void magnet_add_sha1_source(struct magnet_resource *res, const struct sha1 *sha1, const host_addr_t addr, const uint16 port, const struct guid *guid, const gnet_host_vec_t *proxies) { struct magnet_source *s; g_return_if_fail(res); g_return_if_fail(sha1); g_return_if_fail(!res->sha1 || sha1_eq(res->sha1, sha1)); g_return_if_fail(guid != NULL || port_is_valid(port)); if (!res->sha1) { magnet_set_sha1(res, sha1); } s = magnet_source_new(); s->addr = addr; s->port = port; s->sha1 = atom_sha1_get(sha1); s->guid = guid ? atom_guid_get(guid) : NULL; if (proxies != NULL) { int i, n; GSList *sl = NULL; n = gnet_host_vec_count(proxies); for (i = 0; i < n; i++) { gnet_host_t host; host = gnet_host_vec_get(proxies, i); sl = g_slist_prepend(sl, gnet_host_dup(&host)); } s->proxies = sl; } magnet_add_source(res, s); }
static struct magnet_source * magnet_parse_path(const char *path, const char **error_str) { static const struct magnet_source zero_ms; struct magnet_source ms; const char *p, *endptr; clear_error_str(&error_str); g_return_val_if_fail(path, NULL); ms = zero_ms; p = path; if ('/' != *p) { *error_str = "Expected path starting with '/'"; /* Skip this parameter */ return NULL; } g_assert(*p == '/'); endptr = is_strprefix(p, "/uri-res/N2R?"); if (endptr) { struct sha1 sha1; p = endptr; if (!urn_get_sha1(p, &sha1)) { *error_str = "Bad SHA1 in MAGNET URI"; return NULL; } ms.sha1 = atom_sha1_get(&sha1); } else { ms.path = atom_str_get(p); } return wcopy(&ms, sizeof ms); }
static void magnet_handle_key(struct magnet_resource *res, const char *name, const char *value) { char *to_free = NULL; g_return_if_fail(res); g_return_if_fail(name); g_return_if_fail(value); if (!utf8_is_valid_string(value)) { const char *encoding; char *result; g_message("MAGNET URI key \"%s\" is not UTF-8 encoded", name); if (MAGNET_KEY_DISPLAY_NAME != magnet_key_get(name)) return; result = unknown_to_utf8(value, &encoding); if (result != value) { to_free = result; } value = result; g_message("assuming MAGNET URI key \"%s\" is %s encoded", name, encoding); } switch (magnet_key_get(name)) { case MAGNET_KEY_DISPLAY_NAME: if (!res->display_name) { magnet_set_display_name(res, value); } break; case MAGNET_KEY_ALTERNATE_SOURCE: case MAGNET_KEY_EXACT_SOURCE: { struct magnet_source *ms; const char *error; ms = magnet_parse_exact_source(value, &error); if (ms) { if (!res->sha1 && ms->sha1) { res->sha1 = atom_sha1_get(ms->sha1); } if (!ms->sha1 || sha1_eq(res->sha1, ms->sha1)) { res->sources = g_slist_prepend(res->sources, ms); } else { magnet_source_free(&ms); } } else { g_message("could not parse source \"%s\" in MAGNET URI: %s", value, NULL_STRING(error)); } } break; case MAGNET_KEY_EXACT_TOPIC: if (!magnet_set_exact_topic(res, value)) { g_message("MAGNET URI contained unsupported exact topic \"%s\"", value); } break; case MAGNET_KEY_KEYWORD_TOPIC: magnet_add_search(res, value); break; case MAGNET_KEY_EXACT_LENGTH: { int error; uint64 u; u = parse_uint64(value, NULL, 10, &error); if (!error) { magnet_set_filesize(res, u); } } break; case MAGNET_KEY_PARQ_ID: magnet_set_parq_id(res, value); break; case MAGNET_KEY_VENDOR: magnet_set_vendor(res, value); break; case MAGNET_KEY_GUID: magnet_set_guid(res, value); break; case MAGNET_KEY_DHT: { int error; uint8 u; u = parse_uint8(value, NULL, 10, &error); if (!error) { magnet_set_dht(res, u); } } break; case MAGNET_KEY_NONE: g_message("unhandled parameter in MAGNET URI: \"%s\"", name); break; case NUM_MAGNET_KEYS: g_assert_not_reached(); } G_FREE_NULL(to_free); }
kuid_t * kuid_get_atom(const kuid_t *id) { return (kuid_t *) atom_sha1_get((const struct sha1 *) id); }
/** * Locate statistics structure for the file. * * If a SHA1 is given, we search by SHA1. Otherwise we search by (name, size) * and if the record is missing the SHA1, probably because it was not * available at the time of insertion, then it is added to the structure * and recorded as such. */ static struct ul_stats * upload_stats_find(const struct sha1 *sha1, const char *pathname, guint64 size) { struct ul_stats *s = NULL; if (upload_stats_list) { static const struct ul_stats zero_stats; struct ul_stats key; gconstpointer orig_key; g_assert(upload_stats_by_sha1); if (sha1) { s = g_hash_table_lookup(upload_stats_by_sha1, sha1); if (s) goto done; /* Found it by SHA1 */ } key = zero_stats; key.pathname = atom_str_get(pathname); key.size = size; if (hash_list_find(upload_stats_list, &key, &orig_key)) s = deconstify_gpointer(orig_key); atom_str_free_null(&key.pathname); if (s && sha1) { /* Was missing from the by-SHA1 table */ if (NULL == s->sha1) { /* SHA1 was unknown */ s->sha1 = atom_sha1_get(sha1); } else { /* SHA1 changed, file was modified */ struct ul_stats *old = g_hash_table_lookup(upload_stats_by_sha1, s->sha1); g_assert(old == s); /* Must be the same filename entry */ g_hash_table_remove(upload_stats_by_sha1, s->sha1); atom_sha1_free(s->sha1); s->sha1 = atom_sha1_get(sha1); } gm_hash_table_insert_const(upload_stats_by_sha1, s->sha1, s); } } done: /* We guarantee the SHA1 is present in the record if known */ g_assert(!(s && sha1) || s->sha1); /* Postcondition: if we return something, it must be "correct" */ if (s != NULL) { g_assert(atom_is_str(s->pathname)); g_assert(atom_is_str(s->filename)); g_assert(s->norm >= 0.0); } return s; }