-
-/**
- * schedule mhd
- *
- * @param hd a http daemon list entry
- */
-static void
-run_httpd (struct MhdHttpList *hd);
-
-
-/**
- * schedule all mhds
- *
- */
-static void
-run_httpds (void);
-
-
-/**
- * Task run whenever HTTP server operations are pending.
- *
- * @param cls unused
- * @param tc sched context
- */
-static void
-do_httpd (void *cls,
- const struct GNUNET_SCHEDULER_TaskContext *tc);
-
-
-static void
-run_mhd_now (struct MhdHttpList *hd)
-{
- if (GNUNET_SCHEDULER_NO_TASK != hd->httpd_task)
- {
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: killing old task\n");
- GNUNET_SCHEDULER_cancel (hd->httpd_task);
- }
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: Scheduling MHD now\n");
- hd->httpd_task = GNUNET_SCHEDULER_add_now (&do_httpd, hd);
-}
-
-
-/**
- * Ask cURL for the select sets and schedule download
- */
-static void
-curl_download_prepare (void);
-
-
-/**
- * Callback to free content
- *
- * @param cls content to free
- * @param tc task context
- */
-static void
-mhd_content_free (void *cls,
- const struct GNUNET_SCHEDULER_TaskContext *tc)
-{
- struct ProxyCurlTask *ctask = cls;
- struct ProxyUploadData *pdata;
-
- GNUNET_assert (NULL == ctask->pp_match_head);
- if (NULL != ctask->headers)
- curl_slist_free_all (ctask->headers);
-
- if (NULL != ctask->headers)
- curl_slist_free_all (ctask->resolver);
-
- if (NULL != ctask->response)
- MHD_destroy_response (ctask->response);
-
- if (NULL != ctask->post_handler)
- MHD_destroy_post_processor (ctask->post_handler);
-
- if (GNUNET_SCHEDULER_NO_TASK != ctask->pp_task)
- GNUNET_SCHEDULER_cancel (ctask->pp_task);
-
- for (pdata = ctask->upload_data_head; NULL != pdata; pdata = ctask->upload_data_head)
- {
- GNUNET_CONTAINER_DLL_remove (ctask->upload_data_head,
- ctask->upload_data_tail,
- pdata);
- GNUNET_free_non_null (pdata->filename);
- GNUNET_free_non_null (pdata->content_type);
- GNUNET_free_non_null (pdata->key);
- GNUNET_free_non_null (pdata->value);
- GNUNET_free (pdata);
- }
- GNUNET_free (ctask);
-}
-
-
-/**
- * Callback for MHD response
- *
- * @param cls closure
- * @param pos in buffer
- * @param buf buffer
- * @param max space in buffer
- * @return number of bytes written
- */
-static ssize_t
-mhd_content_cb (void *cls,
- uint64_t pos,
- char* buf,
- size_t max)
-{
- struct ProxyCurlTask *ctask = cls;
- struct ProxyREMatch *re_match;
- ssize_t copied = 0;
- size_t bytes_to_copy = ctask->buffer_write_ptr - ctask->buffer_read_ptr;
-
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: content cb for %s. To copy: %u\n",
- ctask->url, (unsigned int) bytes_to_copy);
- if ((GNUNET_YES == ctask->download_is_finished) &&
- (GNUNET_NO == ctask->download_error) &&
- (0 == bytes_to_copy))
- {
- GNUNET_log (GNUNET_ERROR_TYPE_INFO,
- "MHD: sending response for %s\n", ctask->url);
- ctask->download_in_progress = GNUNET_NO;
- run_mhd_now (ctask->mhd);
- GNUNET_SCHEDULER_add_now (&mhd_content_free, ctask);
- total_mhd_connections--;
- return MHD_CONTENT_READER_END_OF_STREAM;
- }
-
- if ((GNUNET_YES == ctask->download_error) &&
- (GNUNET_YES == ctask->download_is_finished) &&
- (0 == bytes_to_copy))
- {
- GNUNET_log (GNUNET_ERROR_TYPE_INFO,
- "MHD: sending error response\n");
- ctask->download_in_progress = GNUNET_NO;
- run_mhd_now (ctask->mhd);
- GNUNET_SCHEDULER_add_now (&mhd_content_free, ctask);
- total_mhd_connections--;
- return MHD_CONTENT_READER_END_WITH_ERROR;
- }
-
- if ( ctask->buf_status == BUF_WAIT_FOR_CURL )
- return 0;
-
- copied = 0;
- for (re_match = ctask->pp_match_head; NULL != re_match; re_match = ctask->pp_match_head)
- {
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: Processing PP %s\n",
- re_match->hostname);
- bytes_to_copy = re_match->start - ctask->buffer_read_ptr;
- if (bytes_to_copy+copied > max)
- {
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: buffer in response too small for %u. Using available space (%d). (%s)\n",
- (unsigned int) bytes_to_copy,
- max,
- ctask->url);
- memcpy (buf+copied, ctask->buffer_read_ptr, max-copied);
- ctask->buffer_read_ptr += max-copied;
- copied = max;
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: copied %d bytes\n", (int) copied);
- return copied;
- }
-
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: copying %u bytes to mhd response at offset %d\n",
- (unsigned int) bytes_to_copy, ctask->buffer_read_ptr);
- memcpy (buf+copied, ctask->buffer_read_ptr, bytes_to_copy);
- copied += bytes_to_copy;
-
- if (GNUNET_NO == re_match->done)
- {
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: Waiting for PP of %s\n", re_match->hostname);
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: copied %d bytes\n", (int) copied);
- ctask->buffer_read_ptr += bytes_to_copy;
- return copied;
- }
-
- if (strlen (re_match->result) > (max - copied))
- {
- //FIXME partially copy domain here
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: buffer in response too small for %s! (%s)\n",
- re_match->result,
- ctask->url);
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: copied %d bytes\n", (int) copied);
- ctask->buffer_read_ptr += bytes_to_copy;
- return copied;
- }
-
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: Adding PP result %s to buffer\n",
- re_match->result);
- memcpy (buf + copied, re_match->result, strlen (re_match->result));
- copied += strlen (re_match->result);
- ctask->buffer_read_ptr = re_match->end;
- GNUNET_CONTAINER_DLL_remove (ctask->pp_match_head,
- ctask->pp_match_tail,
- re_match);
- GNUNET_free (re_match);
- }
-
- bytes_to_copy = ctask->buffer_write_ptr - ctask->buffer_read_ptr;
-
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: copied: %d left: %u, space left in buf: %d\n",
- copied,
- (unsigned int) bytes_to_copy, (int) (max - copied));
-
- if (GNUNET_NO == ctask->download_is_finished)
- {
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: Purging buffer\n");
- memmove (ctask->buffer, ctask->buffer_read_ptr, bytes_to_copy);
- ctask->buffer_read_ptr = ctask->buffer;
- ctask->buffer_write_ptr = ctask->buffer + bytes_to_copy;
- ctask->buffer[bytes_to_copy] = '\0';
- }
-
- if (bytes_to_copy + copied > max)
- bytes_to_copy = max - copied;
- memcpy (buf+copied, ctask->buffer_read_ptr, bytes_to_copy);
- ctask->buffer_read_ptr += bytes_to_copy;
- copied += bytes_to_copy;
- ctask->buf_status = BUF_WAIT_FOR_CURL;
-
- if (NULL != ctask->curl)
- curl_easy_pause (ctask->curl, CURLPAUSE_CONT);
-
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "MHD: copied %d bytes\n", (int) copied);
- run_mhd_now (ctask->mhd);
- return copied;
-}
-
-
-/**
- * Shorten result callback
- *
- * @param cls the proxycurltask
- * @param short_name the shortened name (NULL on error)
- */
-static void
-process_shorten (void* cls, const char* short_name)
-{
- struct ProxyREMatch *re_match = cls;
- char result[sizeof (re_match->result)];
-
- if (NULL == short_name)
- {
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "PP: Unable to shorten %s\n",
- re_match->hostname);
- GNUNET_CONTAINER_DLL_remove (re_match->ctask->pp_match_head,
- re_match->ctask->pp_match_tail,
- re_match);
- GNUNET_free (re_match);
- return;
- }
-
- if (0 == strcmp (short_name, re_match->ctask->leho))
- strcpy (result, re_match->ctask->host);
- else
- strcpy (result, short_name);
-
- GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
- "PP: Shorten %s -> %s\n",
- re_match->hostname,
- result);
-
- if (re_match->is_ssl)
- sprintf (re_match->result, "href=\"https://%s", result);
- else
- sprintf (re_match->result, "href=\"http://%s", result);
-
- re_match->done = GNUNET_YES;
- run_mhd_now (re_match->ctask->mhd);
-}
-
-
-/**
- * Postprocess data in buffer. From read ptr to write ptr
- *
- * @param cls the curlproxytask
- * @param tc task context
- */
-static void
-postprocess_buffer (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)