/** * Writes the browse host data of the context ``ctx'' to the buffer * ``dest''. This must be called multiple times to retrieve the complete * data until zero is returned i.e., the end of file is reached. * * This routine deals with query hit data generation. * * @param ctx an initialized browse host context. * @param dest the destination buffer. * @param size the amount of bytes ``dest'' can hold. * * @return -1 on failure, zero at the end-of-file condition or if size * was zero. On success, the amount of bytes copied to ``dest'' * is returned. */ static ssize_t browse_host_read_qhits(struct special_upload *ctx, void *const dest, size_t size) { struct browse_host_upload *bh = cast_to_browse_host_upload(ctx); size_t remain = size; char *p = dest; /* * If we have no hit pending that we can send, build some more. */ if (NULL == bh->hits) { pslist_t *files = NULL, *sl; int i; for (i = 0; i < BH_SCAN_AHEAD; i++) { shared_file_t *sf; do { /* Skip holes in indices */ bh->file_index++; sf = shared_file_sorted(bh->file_index); } while (NULL == sf && bh->file_index <= shared_files_scanned()); if (SHARE_REBUILDING == sf || NULL == sf) break; files = pslist_prepend(files, sf); } if (NULL == files) /* Did not find any more file to include */ return 0; /* We're done */ /* * Now build the query hits containing the files we selected. */ files = pslist_reverse(files); /* Preserve order */ if (bh->flags & BH_F_G2) { g2_build_qh2_results(files, i, BH_MAX_QH2_SIZE, browse_host_record_qh2, bh, &blank_guid, 0); } else { qhit_build_results(files, i, BH_MAX_QHIT_SIZE, browse_host_record_hit, bh, &blank_guid, 0, &zero_array); } g_assert(bh->hits != NULL); /* At least 1 hit enqueued */ bh->hits = pslist_reverse(bh->hits); /* Preserve order */ PSLIST_FOREACH(files, sl) { shared_file_t *sf = sl->data; shared_file_unref(&sf); }
static pslist_t * resolve_hostname(const char *host, enum net_type net) #ifdef HAS_GETADDRINFO { static const struct addrinfo zero_hints; struct addrinfo hints, *ai, *ai0 = NULL; hset_t *hs; pslist_t *sl_addr; int error; g_assert(host); hints = zero_hints; hints.ai_family = net_type_to_pf(net); error = getaddrinfo(host, NULL, &hints, &ai0); if (error) { g_message("getaddrinfo() failed for \"%s\": %s", host, gai_strerror(error)); return NULL; } sl_addr = NULL; hs = hset_create_any(host_addr_hash_func, NULL, host_addr_eq_func); for (ai = ai0; ai; ai = ai->ai_next) { host_addr_t addr; if (!ai->ai_addr) continue; addr = addrinfo_to_addr(ai); if (is_host_addr(addr) && !hset_contains(hs, &addr)) { host_addr_t *addr_copy; addr_copy = WCOPY(&addr); sl_addr = pslist_prepend(sl_addr, addr_copy); hset_insert(hs, addr_copy); } } hset_free_null(&hs); if (ai0) freeaddrinfo(ai0); return pslist_reverse(sl_addr); }