Some SFTP refactoring
This commit is contained in:
parent
be2138b5a4
commit
68d25d195d
6
Makefile
6
Makefile
@ -39,7 +39,7 @@ endif
|
|||||||
# Platform compiler flags
|
# Platform compiler flags
|
||||||
ifeq ($(OS),Darwin)
|
ifeq ($(OS),Darwin)
|
||||||
CXX = $(shell wx-config --cxx) -D__WXMAC__ -D_WCHAR_H_CPLUSPLUS_98_CONFORMANCE_ -std=gnu++11
|
CXX = $(shell wx-config --cxx) -D__WXMAC__ -D_WCHAR_H_CPLUSPLUS_98_CONFORMANCE_ -std=gnu++11
|
||||||
LDLIBS += /usr/local/lib/libssh2.a
|
LDLIBS += $(shell pkg-config libssh2 --libs)
|
||||||
else
|
else
|
||||||
LDLIBS += -lssh2
|
LDLIBS += -lssh2
|
||||||
endif
|
endif
|
||||||
@ -47,7 +47,7 @@ endif
|
|||||||
ifeq ($(OS),Windows_NT)
|
ifeq ($(OS),Windows_NT)
|
||||||
CXXFLAGS += -static
|
CXXFLAGS += -static
|
||||||
CXX += -std=gnu++11 -Wno-unknown-pragmas -Wno-missing-field-initializers -I/include -DWIN32
|
CXX += -std=gnu++11 -Wno-unknown-pragmas -Wno-missing-field-initializers -I/include -DWIN32
|
||||||
LDLIBS += -L/lib -lwsock32
|
LDLIBS += -L/lib -lws2_32 -lssh2
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(OS),Linux)
|
ifeq ($(OS),Linux)
|
||||||
@ -158,7 +158,7 @@ $(TESTS):
|
|||||||
|
|
||||||
.PHONY: tests
|
.PHONY: tests
|
||||||
tests: $(TESTS) json_wrapper $(BASE_LIB) $(WIDGET_LIB)
|
tests: $(TESTS) json_wrapper $(BASE_LIB) $(WIDGET_LIB)
|
||||||
$(CXX) $(CXXFLAGS) $(WX_CXXFLAGS) tests/main.cpp $(TESTS) $(WIDGET_LIB) $(BASE_LIB) $(WX_LDLIBS) $(LDLIBS) -o tests/runner
|
$(CXX) $(CXXFLAGS) $(WX_CXXFLAGS) tests/main.cpp $(TESTS) $(WIDGET_LIB) $(BASE_LIB) $(LDLIBS) $(WX_LDLIBS) -o tests/runner
|
||||||
|
|
||||||
|
|
||||||
run-tests: tests
|
run-tests: tests
|
||||||
|
@ -1,23 +1,47 @@
|
|||||||
#include "SFTP.h"
|
#include "SFTP.h"
|
||||||
|
|
||||||
SFTP::SFTP(const char *host, const char *user, const char *pass, const char *port)
|
/**
|
||||||
|
* Basic username/password auth
|
||||||
|
* @param string host
|
||||||
|
* @param string user
|
||||||
|
* @param string pass
|
||||||
|
* @param string base_path
|
||||||
|
* @param string port
|
||||||
|
*/
|
||||||
|
SFTP::SFTP(const char *host, const char *user, const char *pass, const char *base_path, const char *port)
|
||||||
{
|
{
|
||||||
this->ssh_connect(host, user, pass, port);
|
this->create_socket(host, port);
|
||||||
|
|
||||||
|
// Create ssh session
|
||||||
|
this->ssh_connect();
|
||||||
|
|
||||||
|
// Authenticate (by password)
|
||||||
|
if (libssh2_userauth_password(this->session, user, pass))
|
||||||
|
{
|
||||||
|
cerr << "Authentication by password failed." << endl;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Create sftp session
|
||||||
this->sftp_connect();
|
this->sftp_connect();
|
||||||
};
|
};
|
||||||
|
|
||||||
SFTP::~SFTP() {
|
SFTP::~SFTP() {
|
||||||
libssh2_sftp_shutdown(sftp_session);
|
// Free libssh2 sessions
|
||||||
libssh2_session_disconnect(session, "Normal Shutdown, Thank you for playing");
|
if (this->sftp_session != nullptr)
|
||||||
libssh2_session_free(session);
|
{
|
||||||
#ifdef WIN32
|
libssh2_sftp_shutdown(this->sftp_session);
|
||||||
closesocket(sock);
|
this->sftp_session = nullptr;
|
||||||
#else
|
}
|
||||||
close(sock);
|
if (this->session != nullptr)
|
||||||
#endif
|
{
|
||||||
|
libssh2_session_disconnect(this->session, "Normal Shutdown, Thank you for playing");
|
||||||
|
libssh2_session_free(this->session);
|
||||||
|
this->session = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
libssh2_exit();
|
libssh2_exit();
|
||||||
freeaddrinfo(host_info_list);
|
this->destroy_socket();
|
||||||
freeaddrinfo(&host_info);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
string SFTP::getFingerprint()
|
string SFTP::getFingerprint()
|
||||||
@ -47,12 +71,12 @@ string SFTP::getFile(const char *path)
|
|||||||
string output = "";
|
string output = "";
|
||||||
|
|
||||||
LIBSSH2_SFTP_HANDLE *sftp_handle;
|
LIBSSH2_SFTP_HANDLE *sftp_handle;
|
||||||
sftp_handle = libssh2_sftp_open(sftp_session, path, LIBSSH2_FXF_READ, 0);
|
sftp_handle = libssh2_sftp_open(this->sftp_session, path, LIBSSH2_FXF_READ, 0);
|
||||||
|
|
||||||
if ( ! sftp_handle)
|
if ( ! sftp_handle)
|
||||||
{
|
{
|
||||||
cerr << "Unable to open file with SFTP: ";
|
cerr << "Unable to open file with SFTP: ";
|
||||||
cerr << libssh2_sftp_last_error(sftp_session) << endl;
|
cerr << libssh2_sftp_last_error(this->sftp_session) << endl;
|
||||||
return output;
|
return output;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -60,7 +84,7 @@ string SFTP::getFile(const char *path)
|
|||||||
char mem[1024];
|
char mem[1024];
|
||||||
|
|
||||||
// loop until fail
|
// loop until fail
|
||||||
rc = libssh2_sftp_read(sftp_handle, mem, sizeof(mem));
|
int rc = libssh2_sftp_read(sftp_handle, mem, sizeof(mem));
|
||||||
|
|
||||||
if (rc > 0)
|
if (rc > 0)
|
||||||
{
|
{
|
||||||
@ -75,7 +99,7 @@ string SFTP::getFile(const char *path)
|
|||||||
return output;
|
return output;
|
||||||
}
|
}
|
||||||
|
|
||||||
void SFTP::ssh_connect(const char *host, const char *user, const char *pass, const char *port)
|
void SFTP::create_socket(const char *host, const char *port)
|
||||||
{
|
{
|
||||||
#ifdef WIN32
|
#ifdef WIN32
|
||||||
WSADATA wsadata;
|
WSADATA wsadata;
|
||||||
@ -92,18 +116,47 @@ void SFTP::ssh_connect(const char *host, const char *user, const char *pass, con
|
|||||||
// Clear out memory in addr structure
|
// Clear out memory in addr structure
|
||||||
memset(&host_info, 0, sizeof host_info);
|
memset(&host_info, 0, sizeof host_info);
|
||||||
|
|
||||||
host_info.ai_family = AF_UNSPEC;
|
host_info.ai_family = AF_UNSPEC; // IPv4/IPv6
|
||||||
host_info.ai_socktype = SOCK_STREAM;
|
host_info.ai_socktype = SOCK_STREAM; // TCP stream sockets
|
||||||
|
host_info.ai_flags = AI_PASSIVE; // fill in my IP for me
|
||||||
|
|
||||||
status = getaddrinfo(host, port, &host_info, &host_info_list);
|
int status = getaddrinfo(host, port, &host_info, &host_info_list);
|
||||||
|
|
||||||
if (status != 0)
|
if (status != 0)
|
||||||
{
|
{
|
||||||
cerr << "getaddrinfo error" << gai_strerror(status) << endl;
|
cerr << "getaddrinfo error: " << gai_strerror(status) << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
this->sock = socket(
|
||||||
|
host_info_list->ai_family,
|
||||||
|
host_info_list->ai_socktype,
|
||||||
|
host_info_list->ai_protocol
|
||||||
|
);
|
||||||
|
|
||||||
|
if (connect(this->sock, host_info_list->ai_addr, host_info_list->ai_addrlen) != 0)
|
||||||
|
{
|
||||||
|
cerr << "Failed to connect to socket." << endl;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void SFTP::destroy_socket()
|
||||||
|
{
|
||||||
|
#ifdef WIN32
|
||||||
|
closesocket(sock);
|
||||||
|
WSACleanup();
|
||||||
|
#else
|
||||||
|
close(sock);
|
||||||
|
|
||||||
|
freeaddrinfo(host_info_list);
|
||||||
|
freeaddrinfo(&host_info);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
void SFTP::ssh_connect()
|
||||||
|
{
|
||||||
// Start libssh2
|
// Start libssh2
|
||||||
rc = libssh2_init(0);
|
int rc = libssh2_init(0);
|
||||||
|
|
||||||
if (rc != 0)
|
if (rc != 0)
|
||||||
{
|
{
|
||||||
@ -111,21 +164,13 @@ void SFTP::ssh_connect(const char *host, const char *user, const char *pass, con
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
sock = socket(AF_INET, SOCK_STREAM, 0);
|
this->session = libssh2_session_init();
|
||||||
|
|
||||||
if (connect(sock, host_info_list->ai_addr, host_info_list->ai_addrlen) != 0)
|
// Since we have set non-blocking, tell libssh2 we are blocking
|
||||||
{
|
libssh2_session_set_blocking(this->session, 1);
|
||||||
cerr << "Failed to connect to socket." << endl;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
session = libssh2_session_init();
|
|
||||||
|
|
||||||
/* Since we have set non-blocking, tell libssh2 we are blocking */
|
|
||||||
libssh2_session_set_blocking(session, 1);
|
|
||||||
|
|
||||||
// Actually do the ssh handshake
|
// Actually do the ssh handshake
|
||||||
rc = libssh2_session_handshake(session, sock);
|
rc = libssh2_session_handshake(this->session, this->sock);
|
||||||
|
|
||||||
if (rc)
|
if (rc)
|
||||||
{
|
{
|
||||||
@ -134,20 +179,13 @@ void SFTP::ssh_connect(const char *host, const char *user, const char *pass, con
|
|||||||
}
|
}
|
||||||
|
|
||||||
//@TODO do something with the handling of known hosts
|
//@TODO do something with the handling of known hosts
|
||||||
|
|
||||||
// Authenticate (by password)
|
|
||||||
if (libssh2_userauth_password(session, user, pass))
|
|
||||||
{
|
|
||||||
cerr << "Authentication by password failed." << endl;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void SFTP::sftp_connect()
|
void SFTP::sftp_connect()
|
||||||
{
|
{
|
||||||
sftp_session = libssh2_sftp_init(session);
|
this->sftp_session = libssh2_sftp_init(this->session);
|
||||||
|
|
||||||
if ( ! sftp_session)
|
if ( ! this->sftp_session)
|
||||||
{
|
{
|
||||||
cerr << "Unable to start SFTP session" << endl;
|
cerr << "Unable to start SFTP session" << endl;
|
||||||
return;
|
return;
|
||||||
|
@ -17,8 +17,10 @@
|
|||||||
// Define this so I actually get functions out of the windows header file
|
// Define this so I actually get functions out of the windows header file
|
||||||
#undef _WIN32_WINNT
|
#undef _WIN32_WINNT
|
||||||
#define _WIN32_WINNT 0x0501
|
#define _WIN32_WINNT 0x0501
|
||||||
#include <Ws2tcpip.h>
|
#include <winsock2.h>
|
||||||
|
#include <ws2tcpip.h>
|
||||||
#else
|
#else
|
||||||
|
#include <sys/types.h>
|
||||||
#include <sys/socket.h>
|
#include <sys/socket.h>
|
||||||
#include <netdb.h>
|
#include <netdb.h>
|
||||||
#endif
|
#endif
|
||||||
@ -31,20 +33,23 @@
|
|||||||
|
|
||||||
class SFTP {
|
class SFTP {
|
||||||
public:
|
public:
|
||||||
SFTP(const char *host, const char *user, const char *pass, const char *port="22");
|
SFTP(const char *host, const char *user, const char *pass, const char *base_path="~", const char *port="22");
|
||||||
~SFTP();
|
~SFTP();
|
||||||
string getFingerprint();
|
string getFingerprint();
|
||||||
string getFile(const char *path);
|
string getFile(const char *path);
|
||||||
|
bool createDir(const char *path);
|
||||||
|
bool writeFile(const char *path, const char *data);
|
||||||
|
//StringVector getDirList(const char *path);
|
||||||
private:
|
private:
|
||||||
struct addrinfo host_info;
|
struct addrinfo host_info;
|
||||||
struct addrinfo *host_info_list;
|
struct addrinfo *host_info_list = nullptr;
|
||||||
const char *fingerprint;
|
const char *fingerprint;
|
||||||
int sock;
|
int sock;
|
||||||
int status;
|
LIBSSH2_SESSION *session = nullptr;
|
||||||
int rc;
|
LIBSSH2_SFTP *sftp_session = nullptr;
|
||||||
LIBSSH2_SESSION *session;
|
void create_socket(const char *host, const char *port);
|
||||||
LIBSSH2_SFTP *sftp_session;
|
void destroy_socket();
|
||||||
void ssh_connect(const char *host, const char *user, const char *pass, const char *port);
|
void ssh_connect();
|
||||||
void sftp_connect();
|
void sftp_connect();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -22,5 +22,10 @@ typedef Json::Value JsonValue;
|
|||||||
typedef Json::Reader JsonReader;
|
typedef Json::Reader JsonReader;
|
||||||
typedef Json::Writer JsonWriter;
|
typedef Json::Writer JsonWriter;
|
||||||
|
|
||||||
|
// Typedef some common templates
|
||||||
|
typedef map<string, int> StringConstMap;
|
||||||
|
typedef map<string, string> StringMap;
|
||||||
|
typedef vector<string> StringVector;
|
||||||
|
|
||||||
#endif // TYRO_COMMON_H
|
#endif // TYRO_COMMON_H
|
||||||
|
|
||||||
|
@ -45,10 +45,6 @@ const int TYRO_DEFAULT_FONT_SIZE = 14;
|
|||||||
const int TYRO_DEFAULT_FONT_SIZE = 10;
|
const int TYRO_DEFAULT_FONT_SIZE = 10;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// Typedef some common templates
|
|
||||||
typedef map<string, int> StringConstMap;
|
|
||||||
typedef map<string, string> StringMap;
|
|
||||||
|
|
||||||
// Editor margins
|
// Editor margins
|
||||||
enum myMargins
|
enum myMargins
|
||||||
{
|
{
|
||||||
|
12
tests/SFTPTest.cpp
Normal file
12
tests/SFTPTest.cpp
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
#include "catch.hpp"
|
||||||
|
#include "../src/base/network/SFTP.h"
|
||||||
|
|
||||||
|
TEST_CASE("SFTP Library")
|
||||||
|
{
|
||||||
|
SFTP *sftp = new SFTP("localhost", "user", "pass", "/", "22");
|
||||||
|
|
||||||
|
SECTION("Sanity check")
|
||||||
|
{
|
||||||
|
REQUIRE(sftp != nullptr);
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user