Skip to content

Commit

Permalink
minizip library integration
Browse files Browse the repository at this point in the history
  • Loading branch information
pavik committed Sep 11, 2018
1 parent c2510ad commit 19fee78
Show file tree
Hide file tree
Showing 54 changed files with 13,028 additions and 37 deletions.
2 changes: 2 additions & 0 deletions configure.ac
Original file line number Diff line number Diff line change
Expand Up @@ -1184,6 +1184,8 @@ fi
ac_configure_args="${ac_configure_args} --disable-shared --with-pic"
AC_CONFIG_SUBDIRS([src/secp256k1])

AC_CONFIG_SUBDIRS([src/minizip])

AC_OUTPUT

dnl Taken from https://wiki.debian.org/RpathIssue
Expand Down
15 changes: 12 additions & 3 deletions src/Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
# Distributed under the MIT software license, see the accompanying
# file COPYING or http://www.opensource.org/licenses/mit-license.php.

DIST_SUBDIRS = secp256k1 univalue
DIST_SUBDIRS = secp256k1 univalue minizip

AM_LDFLAGS = $(PTHREAD_CFLAGS) $(LIBTOOL_LDFLAGS) $(HARDENED_LDFLAGS)
AM_CXXFLAGS = $(HARDENED_CXXFLAGS) $(ERROR_CXXFLAGS)
Expand Down Expand Up @@ -36,10 +36,18 @@ $(LIBLEVELDB) $(LIBMEMENV):
OPT="$(AM_CXXFLAGS) $(PIE_FLAGS) $(CXXFLAGS) $(AM_CPPFLAGS) $(CPPFLAGS) -D__STDC_LIMIT_MACROS"
endif

LIBMINIZIP = minizip/libminizip.la

$(LIBMINIZIP):
@echo "Building minizip ..." && $(MAKE) -C $(@D) $(@F) CXX="$(CXX)" \
CC="$(CC)" PLATFORM=$(TARGET_OS) AR="$(AR)" \
OPT="$(AM_CXXFLAGS) $(PIE_FLAGS) $(CXXFLAGS) $(AM_CPPFLAGS) $(CPPFLAGS)"

BITCOIN_CONFIG_INCLUDES=-I$(builddir)/config
BITCOIN_INCLUDES=-I$(builddir) -I$(builddir)/obj $(BOOST_CPPFLAGS) $(LEVELDB_CPPFLAGS) $(CRYPTO_CFLAGS) $(SSL_CFLAGS)

BITCOIN_INCLUDES += -I$(srcdir)/secp256k1/include
BITCOIN_INCLUDES += -I$(srcdir)/minizip
BITCOIN_INCLUDES += $(UNIVALUE_CFLAGS)

LIBBITCOIN_SERVER=libbitcoin_server.a
Expand Down Expand Up @@ -190,6 +198,7 @@ BITCOIN_CORE_H = \
wallet.h \
wallet_ismine.h \
walletdb.h \
ziputil.h \
zmq/zmqabstractnotifier.h \
zmq/zmqconfig.h \
zmq/zmqnotificationinterface.h \
Expand Down Expand Up @@ -408,6 +417,7 @@ libbitcoin_util_a_SOURCES = \
utilstrencodings.cpp \
utilmoneystr.cpp \
utiltime.cpp \
ziputil.cpp \
$(BITCOIN_CORE_H)

if GLIBC_BACK_COMPAT
Expand Down Expand Up @@ -446,9 +456,8 @@ colxd_LDADD = \
$(LIBLEVELDB) \
$(LIBMEMENV) \
$(LIBSECP256K1) \
$(CURL_LIBS)
$(LIBMINIZIP)

# ZCDEV: duplicate? #
colxd_LDADD += $(BOOST_LIBS) $(BDB_LIBS) $(SSL_LIBS) $(CRYPTO_LIBS) $(MINIUPNPC_LIBS) $(EVENT_PTHREADS_LIBS) $(EVENT_LIBS) $(ZMQ_LIBS) $(CURL_LIBS)

# colx-cli binary #
Expand Down
2 changes: 1 addition & 1 deletion src/Makefile.qt.include
Original file line number Diff line number Diff line change
Expand Up @@ -405,7 +405,7 @@ qt_colx_qt_LDADD += $(LIBBITCOIN_ZMQ) $(ZMQ_LIBS)
endif
qt_colx_qt_LDADD += $(LIBBITCOIN_CLI) $(LIBBITCOIN_COMMON) $(LIBBITCOIN_UTIL) $(LIBBITCOIN_CRYPTO) $(LIBUNIVALUE) $(LIBBITCOIN_ZEROCOIN) $(LIBLEVELDB) $(LIBMEMENV) \
$(BOOST_LIBS) $(QT_LIBS) $(QT_DBUS_LIBS) $(QR_LIBS) $(PROTOBUF_LIBS) $(BDB_LIBS) $(SSL_LIBS) $(CRYPTO_LIBS) $(MINIUPNPC_LIBS) $(LIBSECP256K1) $(CURL_LIBS) \
$(EVENT_PTHREADS_LIBS) $(EVENT_LIBS)
$(EVENT_PTHREADS_LIBS) $(EVENT_LIBS) $(LIBMINIZIP)
qt_colx_qt_LDFLAGS = $(RELDFLAGS) $(AM_LDFLAGS) $(QT_LDFLAGS) $(LIBTOOL_APP_LDFLAGS)
qt_colx_qt_LIBTOOLFLAGS = --tag CXX

Expand Down
5 changes: 4 additions & 1 deletion src/Makefile.test.include
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,7 @@ BITCOIN_TESTS =\
test/key_tests.cpp \
test/main_tests.cpp \
test/mempool_tests.cpp \
test/minizip_tests.cpp \
test/mruset_tests.cpp \
test/multisig_tests.cpp \
test/netbase_tests.cpp \
Expand Down Expand Up @@ -96,8 +97,10 @@ endif

test_test_colx_SOURCES = $(BITCOIN_TESTS) $(JSON_TEST_FILES) $(RAW_TEST_FILES)
test_test_colx_CPPFLAGS = $(AM_CPPFLAGS) $(BITCOIN_INCLUDES) -I$(builddir)/test/ $(TESTDEFS)
test_test_colx_LDADD = $(LIBBITCOIN_SERVER) $(LIBBITCOIN_CLI) $(LIBBITCOIN_COMMON) $(LIBBITCOIN_UTIL) $(LIBBITCOIN_CRYPTO) $(LIBUNIVALUE) $(LIBBITCOIN_ZEROCOIN) $(LIBLEVELDB) $(LIBMEMENV) \
test_test_colx_LDADD = $(LIBBITCOIN_SERVER) $(LIBBITCOIN_CLI) $(LIBBITCOIN_COMMON) $(LIBBITCOIN_UTIL) \
$(LIBBITCOIN_CRYPTO) $(LIBUNIVALUE) $(LIBBITCOIN_ZEROCOIN) $(LIBLEVELDB) $(LIBMEMENV) $(LIBMINIZIP) \
$(BOOST_LIBS) $(BOOST_UNIT_TEST_FRAMEWORK_LIB) $(LIBSECP256K1) $(EVENT_LIBS) $(EVENT_PTHREADS_LIBS)

if ENABLE_WALLET
test_test_colx_LDADD += $(LIBBITCOIN_WALLET)
endif
Expand Down
153 changes: 130 additions & 23 deletions src/curl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -49,8 +49,11 @@ struct CurlScopeInit

struct MemoryBuffer
{
char* memory;
size_t size;
MemoryBuffer():
memory(nullptr), size(0) {}

char* memory;
size_t size;
};

static size_t WriteMemoryCallback(void *contents, size_t size, size_t nmemb, void *userp)
Expand All @@ -71,16 +74,43 @@ static size_t WriteMemoryCallback(void *contents, size_t size, size_t nmemb, voi
}
}

static size_t WriteFileCallback(void *contents, size_t size, size_t nmemb, void *userp)
{
size_t written = fwrite(contents, size, nmemb, (FILE*)userp);
return written;
}

struct ProgressData
{
ProgressData():
download(true), fn(nullptr) {}

bool download;
ProgressReport fn;
};

static int ProgressCallback(void *clientp, curl_off_t dltotal, curl_off_t dlnow, curl_off_t ultotal, curl_off_t ulnow)
{
if (clientp) {
ProgressData *pd = reinterpret_cast<ProgressData*>(clientp);
if (pd->download)
return pd->fn(dltotal, dlnow);
else
return pd->fn(ultotal, ulnow);
} else
return 0;
}

//
// public API
//

bool CURLGetRedirect(const CUrl& url, CUrl& redirect, string& error)
{
CurlScopeInit curl;
CURLcode res;
char *location;
long response_code;
CURLcode res = CURLE_OK;
char *location = nullptr;
long response_code = 0;

redirect.clear();
error.clear();
Expand Down Expand Up @@ -129,7 +159,7 @@ bool CURLGetRedirect(const CUrl& url, CUrl& redirect, string& error)
}


bool CURLDownloadToMem(const CUrl& url, string& buff, string& error)
bool CURLDownloadToMem(const CUrl& url, ProgressReport fn, string& buff, string& error)
{
CurlScopeInit curl;
CURLcode res;
Expand Down Expand Up @@ -168,34 +198,111 @@ bool CURLDownloadToMem(const CUrl& url, string& buff, string& error)
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 0L);
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, 0L);

/* follow max 3 redirects */
curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1L);
curl_easy_setopt(curl, CURLOPT_MAXREDIRS, 3L);

ProgressData pd;
pd.download = true;
pd.fn = fn;

/* progress meter */
if (fn) {
curl_easy_setopt(curl, CURLOPT_NOPROGRESS, 0L);
curl_easy_setopt(curl, CURLOPT_XFERINFOFUNCTION, ProgressCallback);
curl_easy_setopt(curl, CURLOPT_XFERINFODATA, &pd);
}

/* get it! */
res = curl_easy_perform(curl);

/* check for errors */
if (res != CURLE_OK) {
error = strprintf("curl_easy_perform failed: %s", curl_easy_strerror(res));
} else {
long response_code = 0;
curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &response_code);
if (response_code / 100 != 2) {
error = strprintf("response code is not OK: %d", response_code);
DebugPrintf("%s: response code=%d, response content=%s", __func__, response_code, string(chunk.memory, chunk.size));
} else {
/*
* Now, our chunk.memory points to a memory block that is chunk.size
* bytes big and contains the remote file.
*/
DebugPrintf("%s: %lu bytes retrieved\n", __func__, (long)chunk.size);
buff.assign(chunk.memory, chunk.size);
}
/*
* Now, our chunk.memory points to a memory block that is chunk.size
* bytes big and contains the remote file.
*/
DebugPrintf("%s: %lu bytes retrieved\n", __func__, (long)chunk.size);
buff.assign(chunk.memory, chunk.size);
}

free(chunk.memory);
if (chunk.memory)
free(chunk.memory);

return !buff.empty();
}

bool CURLDownloadToFile(const CUrl& url, const string& path, ProgressReport callback, string& error)
bool CURLDownloadToFile(const CUrl& url, const string& path, ProgressReport fn, string& error)
{
error = "not implemented";
return false;
CurlScopeInit curl;
error.clear();

if (url.empty()) {
error = "url is empty";
return false;
}

if (path.empty()) {
error = "path is empty";
return false;
}

if (!curl.instance()) {
error = "curl init failed";
return false;
}

/* specify URL to get */
curl_easy_setopt(curl, CURLOPT_URL, url.c_str());

/* send all data to this function */
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, WriteFileCallback);

/* open the file */
FILE *pagefile = fopen(path.c_str(), "wb");
if (!pagefile) {
error = strprintf("failed to create file: %s", path);
return false;
}

/* write the page body to this file handle */
curl_easy_setopt(curl, CURLOPT_WRITEDATA, pagefile);

/* some servers don't like requests that are made without a user-agent */
const string agent = FormatFullVersion();
curl_easy_setopt(curl, CURLOPT_USERAGENT, agent.c_str());

/* disable peer and host verification because of issues on Mac and Win */
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 0L);
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, 0L);

/* follow max 3 redirects */
curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1L);
curl_easy_setopt(curl, CURLOPT_MAXREDIRS, 3L);

ProgressData pd;
pd.download = true;
pd.fn = fn;

/* progress meter */
if (fn) {
curl_easy_setopt(curl, CURLOPT_NOPROGRESS, 0L);
curl_easy_setopt(curl, CURLOPT_XFERINFOFUNCTION, ProgressCallback);
curl_easy_setopt(curl, CURLOPT_XFERINFODATA, &pd);
}

/* get it! */
CURLcode res = curl_easy_perform(curl);

/* check for errors */
if (res != CURLE_OK)
error = strprintf("curl_easy_perform failed: %s", curl_easy_strerror(res));

/* close the file */
if (pagefile)
fclose(pagefile);

return CURLE_OK == res;
}
11 changes: 6 additions & 5 deletions src/curl.h
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,8 @@ typedef std::string CUrl;

/**
* Progress callback.
* @param[in] total download size
* @param[in] now downloded by now
* @param[in] total download/upload size total
* @param[in] now downlod/upload size by now
* @return 1 - stop download, 0 - continue download
*/
typedef std::function<int (double total, double now)> ProgressReport;
Expand All @@ -30,20 +30,21 @@ bool CURLGetRedirect(const CUrl& url, CUrl& redirect, std::string& error);
/**
* Download content to the memory buffer.
* @param[in] url input http(s) address
* @param[in] fn progress report function
* @param[out] buff output buffer
* @param[out] error brief description on fail
* @return true - success, false - fail
*/
bool CURLDownloadToMem(const CUrl& url, std::string& buff, std::string& error);
bool CURLDownloadToMem(const CUrl& url, ProgressReport fn, std::string& buff, std::string& error);

/**
* Download content to the file by given path.
* @param[in] url input http(s) address
* @param[in] path path to the file where to save content
* @param[in] callback progress report function
* @param[in] fn progress report function
* @param[out] error brief description on fail
* @return true - success, false - fail
*/
bool CURLDownloadToFile(const CUrl& url, const std::string& path, ProgressReport callback, std::string& error);
bool CURLDownloadToFile(const CUrl& url, const std::string& path, ProgressReport fn, std::string& error);

#endif // BITCOIN_CURL_H
Loading

0 comments on commit 19fee78

Please sign in to comment.