X-Git-Url: https://main.carlh.net/gitweb/?p=dcpomatic.git;a=blobdiff_plain;f=src%2Flib%2Finternet.cc;h=5a909e470088470e558a4c0461ce5889dcf96f9e;hp=c3f9dce659522099a13b047477494307ecaf3a18;hb=3828baf56467224f5d44049bf1e7a7ed11f43a05;hpb=8f9c5e06afd3c0255ed484a495b1ddad7fd83205 diff --git a/src/lib/internet.cc b/src/lib/internet.cc index c3f9dce65..5a909e470 100644 --- a/src/lib/internet.cc +++ b/src/lib/internet.cc @@ -1,37 +1,42 @@ /* - Copyright (C) 2014 Carl Hetherington + Copyright (C) 2014-2015 Carl Hetherington - This program is free software; you can redistribute it and/or modify + This file is part of DCP-o-matic. + + DCP-o-matic is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. - This program is distributed in the hope that it will be useful, + DCP-o-matic is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + along with DCP-o-matic. If not, see . */ -#include +#include "scoped_temporary.h" +#include "compose.hpp" +#include "safe_stringstream.h" +#include "exceptions.h" +#include +#include #include #include #include -#include -#include -#include "util.h" +#include +#include #include "i18n.h" using std::string; -using std::stringstream; using std::list; using boost::optional; using boost::function; +using boost::algorithm::trim; static size_t get_from_zip_url_data (void* buffer, size_t size, size_t nmemb, void* stream) @@ -45,17 +50,24 @@ get_from_zip_url_data (void* buffer, size_t size, size_t nmemb, void* stream) * @param load Function passed a (temporary) filesystem path of the unpacked file. */ optional -get_from_zip_url (string url, string file, function load) +get_from_zip_url (string url, string file, bool pasv, function load) { /* Download the ZIP file to temp_zip */ CURL* curl = curl_easy_init (); curl_easy_setopt (curl, CURLOPT_URL, url.c_str ()); - + ScopedTemporary temp_zip; FILE* f = temp_zip.open ("wb"); curl_easy_setopt (curl, CURLOPT_WRITEFUNCTION, get_from_zip_url_data); curl_easy_setopt (curl, CURLOPT_WRITEDATA, f); curl_easy_setopt (curl, CURLOPT_FTP_USE_EPSV, 0); + curl_easy_setopt (curl, CURLOPT_FTP_USE_EPRT, 0); + if (!pasv) { + curl_easy_setopt (curl, CURLOPT_FTPPORT, "-"); + } + + /* Maximum time is 20s */ + curl_easy_setopt (curl, CURLOPT_TIMEOUT, 20); CURLcode const cr = curl_easy_perform (curl); @@ -66,21 +78,21 @@ get_from_zip_url (string url, string file, function (_("Could not open downloaded ZIP file")); } - + struct zip_file* zip_file = zip_fopen (zip, file.c_str(), 0); if (!zip_file) { return optional (_("Unexpected ZIP file contents")); } - + ScopedTemporary temp_cert; f = temp_cert.open ("wb"); char buffer[4096]; - while (1) { + while (true) { int const N = zip_fread (zip_file, buffer, sizeof (buffer)); fwrite (buffer, 1, N, f); if (N < int (sizeof (buffer))) { @@ -88,12 +100,11 @@ get_from_zip_url (string url, string file, function (); } - static size_t ftp_ls_data (void* buffer, size_t size, size_t nmemb, void* data) { @@ -102,21 +113,23 @@ ftp_ls_data (void* buffer, size_t size, size_t nmemb, void* data) for (size_t i = 0; i < (size * nmemb); ++i) { *s += b[i]; } - return nmemb; + return size * nmemb; } list -ftp_ls (string url) +ftp_ls (string url, bool pasv) { CURL* curl = curl_easy_init (); if (!curl) { - return list (); + throw NetworkError ("could not set up curl"); } if (url.substr (url.length() - 1, 1) != "/") { url += "/"; } curl_easy_setopt (curl, CURLOPT_URL, url.c_str ()); + /* 20s timeout */ + curl_easy_setopt (curl, CURLOPT_TIMEOUT, 20); string ls_raw; struct curl_slist* commands = 0; @@ -125,16 +138,22 @@ ftp_ls (string url) curl_easy_setopt (curl, CURLOPT_WRITEDATA, &ls_raw); curl_easy_setopt (curl, CURLOPT_WRITEFUNCTION, ftp_ls_data); curl_easy_setopt (curl, CURLOPT_FTP_USE_EPSV, 0); + curl_easy_setopt (curl, CURLOPT_FTP_USE_EPRT, 0); + curl_easy_setopt (curl, CURLOPT_VERBOSE, 1); + if (!pasv) { + curl_easy_setopt (curl, CURLOPT_FTPPORT, "-"); + } CURLcode const r = curl_easy_perform (curl); if (r != CURLE_OK) { - return list (); + curl_easy_cleanup (curl); + throw NetworkError (curl_easy_strerror (r)); } - stringstream s (ls_raw); - string line; + SafeStringStream s (ls_raw); list ls; while (s.good ()) { - getline (s, line); + string line = s.getline (); + trim (line); if (line.length() > 55) { string const file = line.substr (55); if (file != "." && file != "..") {