--- a/src/network/newgrf_download.cpp Sat Jul 19 01:38:52 2008 +0300
+++ b/src/network/newgrf_download.cpp Tue Jul 22 18:29:06 2008 +0300
@@ -20,6 +20,7 @@
#include "../gfx_func.h"
#include "../querystring_gui.h"
#include "../sortlist_type.h"
+#include "../fileio.h"
#include "../rev.h"
// XXX: ...
@@ -81,7 +82,7 @@
/** Ask the master database about the availablity of the given NewGRFs, and update
* the GRFConfigs that are avilable to GCS_AVAILABLE
* @param config pointer to a linked-list of grfconfig's needed */
-static void CheckAvailableNewGRFs(GRFConfig *list)
+static int CheckAvailableNewGRFs(GRFConfig *list)
{
GRFConfig *c;
int i;
@@ -93,6 +94,8 @@
long http_code;
char *buf_ptr;
CURLcode err;
+ int ret = -1;
+ int found = 0;
// initialize to a safe state for error handling
curl = write_ctx.buf = NULL;
@@ -153,7 +156,7 @@
curl_easy_setopt(curl, CURLOPT_DEBUGFUNCTION, XXX)
*/
|| (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_NOPROGRESS, 1))) // no progress meter on stdout, thx
- || (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_ERRORBUFFER, curl_errbuf))) // human-readable error messages
+ || (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_ERRORBUFFER, curl_errbuf))) // XXX: human-readable error messages
|| (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_URL, api_url))) // the URL to retrieve
|| (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_USERAGENT, useragent))) // the User-agent to use
|| (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_POSTFIELDS, query_buf))) // the POST data
@@ -231,6 +234,9 @@
c->filename = url;
c->status = GCS_AVAILABLE;
+
+ found++;
+
break;
}
}
@@ -243,6 +249,9 @@
// move on to the next line
buf_ptr = nl + 1;
}
+
+ // return number of NewGRFs found, defaults to -1 for errors
+ ret = found;
error :
// cleanup
@@ -250,6 +259,117 @@
if (curl)
curl_easy_cleanup(curl);
+
+ // return as defined by ret
+ return ret;
+}
+
+/** Download the NewGRFs that are listed as GCS_AVAILABLE
+ * @param config pointer to a linked-list of grfconfig's to be downloaded */
+static int DownloadAvailableNewGRFs(GRFConfig *list)
+{
+ GRFConfig *c;
+ CURL *curl = NULL;
+ CURLcode err;
+ FILE *fh = NULL;
+ char md5buf[64], filename[256], useragent[512];
+ long http_code;
+ int ret = -1;
+
+ // set up curl
+ if ((err = do_init_curl())) {
+ DEBUG(grfdl, 0, "curl_global_init failed: %s", curl_easy_strerror(err));
+ goto error;
+ }
+
+ // allocate a new curl_easy
+ if ((curl = curl_easy_init()) == NULL) {
+ DEBUG(grfdl, 0, "curl_easy_init failed");
+ goto error;
+ }
+
+ // our useragent
+ assert(snprintf(useragent, sizeof(useragent), NETWORK_HTTP_USER_AGENT, _openttd_revision) < 512);
+
+ // let's set some options...
+ if (
+ (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_VERBOSE, 1))) // XXX: tie this in with OpenTTD's debug stuff
+ /*
+ curl_easy_setopt(curl, CURLOPT_DEBUGFUNCTION, XXX)
+ */
+ || (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_NOPROGRESS, 1))) // no progress meter on stdout, thx
+// || (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_ERRORBUFFER, curl_errbuf))) // human-readable error messages
+
+ || (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_USERAGENT, useragent))) // the User-agent to use
+
+/*
+ || (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_POSTFIELDS, query_buf))) // the POST data
+ || (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, &check_available_write_cb)))
+*/
+ ) {
+ DEBUG(grfdl, 0, "curl_easy_setopt failed: %s", curl_easy_strerror(err));
+ goto error;
+ }
+
+ // then start looping through the NewGRFs to download
+ for (c = list; c != NULL; c = c->next) {
+ // skip the ones that are not available
+ if (c->status != GCS_AVAILABLE)
+ continue;
+
+ // format the md5sum
+ md5sumToString(md5buf, lastof(md5buf), c->md5sum);
+
+ // snprintf the entry into the query buffer
+ assert(snprintf(filename, sizeof(filename), "%08X-%32s.tar", BSWAP32(c->grfid), md5buf) < 256);
+
+ // open the file
+ if ((fh = FioFOpenFile(filename, "wb", CACHE_DIR)) == NULL) {
+ DEBUG(grfdl, 0, "Opening local GRF file failed: %s", filename);
+ goto error;
+ }
+
+ // set up curl
+ if (
+ (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_URL, c->filename))) // the URL to retrieve
+ || (CURLE_OK != (err = curl_easy_setopt(curl, CURLOPT_WRITEDATA, fh))) // XXX: need to fwrite() ourself
+ ) {
+ DEBUG(grfdl, 0, "curl_easy_setopt failed: %s", curl_easy_strerror(err));
+ goto error;
+ }
+
+ // XXX: currently this freezes the UI..
+ if ((err = curl_easy_perform(curl))) {
+ DEBUG(grfdl, 0, "the curl request failed: %s", curl_easy_strerror(err));
+ goto error;
+ }
+
+ // get the HTTP return code
+ if ((err = curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &http_code))) {
+ DEBUG(grfdl, 0, "curl_easy_getinfo failed: %s", curl_easy_strerror(err));
+ goto error;
+ }
+
+ if (http_code != 200) {
+ DEBUG(grfdl, 0, "Bad HTTP response code: %d", http_code);
+ goto error;
+ }
+
+ // OK, great
+ c->status = GCS_UNKNOWN;
+ }
+
+ // success
+ ret = 0;
+
+error:
+ if (fh)
+ fclose(fh);
+
+ if (curl)
+ curl_easy_cleanup(curl);
+
+ return ret;
}
// XXX: copy-pasted from newgrf_gui.cpp
@@ -473,16 +593,42 @@
virtual void OnClick(Point pt, int widget)
{
+ int found;
+
switch (widget) {
case DNGRFS_CHECK_AVAILABLE:
- CheckAvailableNewGRFs(this->list);
+ // do the HTTP request etc.
+ found = CheckAvailableNewGRFs(this->list);
+
+ if (found < 0) {
+ // failed
+ ShowErrorMessage(INVALID_STRING_ID, STR_NEWGRF_DOWNLOAD_CHECK_FAILED, 0, 0);
+
+ } else if (found == 0) {
+ // no NewGRFs found
+ ShowErrorMessage(INVALID_STRING_ID, STR_NEWGRF_DOWNLOAD_CHECK_NONE, 0, 0);
+
+ } else {
+ // success, flip the button enabled states
+ this->SetWidgetDisabledState(DNGRFS_CHECK_AVAILABLE, 1);
+ this->SetWidgetDisabledState(DNGRFS_DOWNLOAD_AVAILABLE, 0);
+
+ // redraw with new status
+ this->SetDirty();
+ }
- this->SetDirty();
break;
case DNGRFS_DOWNLOAD_AVAILABLE:
- // XXX: implement
+ // do a bunch of HTTP requests
+ found = DownloadAvailableNewGRFs(this->list);
+
+ // disable the button, not useful anymore
+ this->SetWidgetDisabledState(DNGRFS_DOWNLOAD_AVAILABLE, 1);
+
+ // redraw with new status
+ this->SetDirty();
break;
@@ -520,7 +666,7 @@
/* Widget definition of the download newgrfs window */
static const Widget _newgrf_download_widgets[] = {
{ WWT_CLOSEBOX, RESIZE_NONE, 10, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW }, // DNGRFS_CLOSEBOX
-{ WWT_CAPTION, RESIZE_RIGHT, 10, 11, 299, 0, 13, STR_NEWGRF_SETTINGS_CAPTION, STR_018C_WINDOW_TITLE_DRAG_THIS }, // DNGRFS_CAPTION
+{ WWT_CAPTION, RESIZE_RIGHT, 10, 11, 299, 0, 13, STR_NEWGRF_DOWNLOAD_CAPTION, STR_018C_WINDOW_TITLE_DRAG_THIS }, // DNGRFS_CAPTION
{ WWT_PANEL, RESIZE_RIGHT, 10, 0, 299, 14, 29, STR_NULL, STR_NULL }, // DNGRFS_BACKGROUND
/*