This repository was archived by the owner on Jan 20, 2025. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 462
mbed TLS client support, try 2 #48
Open
tve
wants to merge
36
commits into
me-no-dev:master
Choose a base branch
from
tve:mbed-tls-try2
base: master
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Changes from 20 commits
Commits
Show all changes
36 commits
Select commit
Hold shift + click to select a range
a251e59
- very early version with mbed TLS support.
fremouw d4257e6
improved TLS support, removed some not needed debug statements.
fremouw eeff609
removed some more logging.
fremouw f2127a0
getting there, seems to start working, there are still some issues wi…
fremouw 3c9fbd9
add fix for reading larger amounts of data.
fremouw d501a90
some code clean-up
fremouw c9dd608
more code clean-up.
fremouw 52e550b
revert IDF changes, so it works with the latest stable IDF.
fremouw 001ae06
Not a fan of defines, but to keep things in line with the esp8266 ver…
fremouw 9f7a918
clean-up
fremouw 5187673
merge origin/idf-update into mbed-tls, as it's now part of the latest…
fremouw 373c334
Merge branch 'master' into mbed-tls
fremouw d631d7d
add some dummy functions so we can compile when the ESP Async WebServ…
fremouw 78f952e
allow setting a root CA.
fremouw 0879ba2
oops, set debug disabled as default again.
fremouw ef50357
add ASYNC_TCP_SSL_ENABLED around setRootCa call.
fremouw 3fa9abf
Update README.md
fremouw 5e06389
add support for pre-shared key TLS cipher suites
tve 5e511de
update mbed-tls implementation to account for restructing
tve 8e55be4
don't assign _hostname unless necessary
tve 9cba86e
fix indentation; make SSL timeout a #define
tve f34df7f
make SSL timeout a #define, 2nd try
tve 7bca0f4
Merge remote-tracking branch 'upstream/master' into mbed-tls-try2
tve 8ef604b
fix while loop in _recv; fix calls into LwIP; add some comments
tve b7ee312
fix c/c++ linking from tcp_ssl to tcp code
tve 73480f3
TLS fixes: pbuf free bug when reading; add debug printfs; useless ext…
tve 8b52f6c
add minor comment
tve 1e8da66
merge upstream into mbed-tls
tve 8e77fe7
fix Codacy issues
tve b0b2bac
Merge remote-tracking branch 'upstream/master' into mbed-tls-try2
tve 3cc7048
fix issues with closed_slots
tve abdd496
Merge branch 'master' into mbed-tls-try2
me-no-dev 44b3d6b
mbed-tls-try2 updates (#3)
robert-alfaro 540bf7d
fix codacity strlen issues
tve 3d67ffe
Merge branch 'master' into mbed-tls-try2
tve 59f83d8
add client certificate authentication
r3no1t File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -534,6 +534,14 @@ AsyncClient::AsyncClient(tcp_pcb* pcb) | |
, _rx_since_timeout(0) | ||
, _ack_timeout(ASYNC_MAX_ACK_TIME) | ||
, _connect_port(0) | ||
#if ASYNC_TCP_SSL_ENABLED | ||
, _root_ca_len(0) | ||
, _root_ca(NULL) | ||
, _pcb_secure(false) | ||
, _handshake_done(true) | ||
, _psk_ident(0) | ||
, _psk(0) | ||
#endif // ASYNC_TCP_SSL_ENABLED<Paste> | ||
, prev(NULL) | ||
, next(NULL) | ||
{ | ||
|
@@ -571,6 +579,19 @@ AsyncClient& AsyncClient::operator=(const AsyncClient& other){ | |
tcp_sent(_pcb, &_tcp_sent); | ||
tcp_err(_pcb, &_tcp_error); | ||
tcp_poll(_pcb, &_tcp_poll, 1); | ||
#if ASYNC_TCP_SSL_ENABLED | ||
if(tcp_ssl_has(_pcb)){ | ||
_pcb_secure = true; | ||
_handshake_done = false; | ||
tcp_ssl_arg(_pcb, this); | ||
tcp_ssl_data(_pcb, &_s_data); | ||
tcp_ssl_handshake(_pcb, &_s_handshake); | ||
tcp_ssl_err(_pcb, &_s_ssl_error); | ||
} else { | ||
_pcb_secure = false; | ||
_handshake_done = true; | ||
} | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
} | ||
return *this; | ||
} | ||
|
@@ -642,7 +663,11 @@ void AsyncClient::onPoll(AcConnectHandler cb, void* arg){ | |
* Main Public Methods | ||
* */ | ||
|
||
#if ASYNC_TCP_SSL_ENABLED | ||
bool AsyncClient::connect(IPAddress ip, uint16_t port, bool secure){ | ||
#else | ||
bool AsyncClient::connect(IPAddress ip, uint16_t port){ | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
if (_pcb){ | ||
log_w("already connected, state %d", _pcb->state); | ||
return false; | ||
|
@@ -662,6 +687,11 @@ bool AsyncClient::connect(IPAddress ip, uint16_t port){ | |
return false; | ||
} | ||
|
||
#if ASYNC_TCP_SSL_ENABLED | ||
_pcb_secure = secure; | ||
_handshake_done = !secure; | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
|
||
tcp_arg(pcb, this); | ||
tcp_err(pcb, &_tcp_error); | ||
tcp_recv(pcb, &_tcp_recv); | ||
|
@@ -672,13 +702,27 @@ bool AsyncClient::connect(IPAddress ip, uint16_t port){ | |
return true; | ||
} | ||
|
||
#if ASYNC_TCP_SSL_ENABLED | ||
bool AsyncClient::connect(const char* host, uint16_t port, bool secure){ | ||
#else | ||
bool AsyncClient::connect(const char* host, uint16_t port){ | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
ip_addr_t addr; | ||
err_t err = dns_gethostbyname(host, &addr, (dns_found_callback)&_tcp_dns_found, this); | ||
if(err == ERR_OK) { | ||
#if ASYNC_TCP_SSL_ENABLED | ||
_hostname = host; | ||
return connect(IPAddress(addr.u_addr.ip4.addr), port, secure); | ||
#else | ||
return connect(IPAddress(addr.u_addr.ip4.addr), port); | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
} else if(err == ERR_INPROGRESS) { | ||
_connect_port = port; | ||
#if ASYNC_TCP_SSL_ENABLED | ||
_hostname = host; | ||
_pcb_secure = secure; | ||
_handshake_done = !secure; | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
return true; | ||
} | ||
log_e("error: %d", err); | ||
|
@@ -700,6 +744,18 @@ int8_t AsyncClient::abort(){ | |
return ERR_ABRT; | ||
} | ||
|
||
#if ASYNC_TCP_SSL_ENABLED | ||
void AsyncClient::setRootCa(const char* rootca, const size_t len) { | ||
_root_ca = (char*)rootca; | ||
_root_ca_len = len; | ||
} | ||
|
||
void AsyncClient::setPsk(const char* psk_ident, const char* psk) { | ||
_psk_ident = psk_ident; | ||
_psk = psk; | ||
} | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
|
||
size_t AsyncClient::space(){ | ||
if((_pcb != NULL) && (_pcb->state == 4)){ | ||
return tcp_sndbuf(_pcb); | ||
|
@@ -715,6 +771,19 @@ size_t AsyncClient::add(const char* data, size_t size, uint8_t apiflags) { | |
if(!room) { | ||
return 0; | ||
} | ||
#if ASYNC_TCP_SSL_ENABLED | ||
if(_pcb_secure){ | ||
int sent = tcp_ssl_write(_pcb, (uint8_t*)data, size); | ||
if(sent >= 0){ | ||
// @ToDo: ??? | ||
//_tx_unacked_len += sent; | ||
return sent; | ||
} | ||
//log_i("add: tcp_ssl_write: %d", sent); | ||
_close(); | ||
return 0; | ||
} | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
size_t will_send = (room < size) ? room : size; | ||
int8_t err = ERR_OK; | ||
err = _tcp_write(_pcb, data, will_send, apiflags, this); | ||
|
@@ -725,6 +794,9 @@ size_t AsyncClient::add(const char* data, size_t size, uint8_t apiflags) { | |
} | ||
|
||
bool AsyncClient::send(){ | ||
#if ASYNC_TCP_SSL_ENABLED | ||
if(_pcb_secure) return true; | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
int8_t err = ERR_OK; | ||
err = _tcp_output(_pcb, this); | ||
if(err == ERR_OK){ | ||
|
@@ -762,6 +834,11 @@ int8_t AsyncClient::_close(){ | |
int8_t err = ERR_OK; | ||
if(_pcb) { | ||
//log_i(""); | ||
#if ASYNC_TCP_SSL_ENABLED | ||
if(_pcb_secure){ | ||
tcp_ssl_free(_pcb); | ||
} | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
tcp_arg(_pcb, NULL); | ||
tcp_sent(_pcb, NULL); | ||
tcp_recv(_pcb, NULL); | ||
|
@@ -792,15 +869,47 @@ int8_t AsyncClient::_connected(void* pcb, int8_t err){ | |
// tcp_recv(_pcb, &_tcp_recv); | ||
// tcp_sent(_pcb, &_tcp_sent); | ||
// tcp_poll(_pcb, &_tcp_poll, 1); | ||
#if ASYNC_TCP_SSL_ENABLED | ||
if(_pcb_secure){ | ||
bool err = false; | ||
if(_root_ca) { | ||
err = tcp_ssl_new_client(_pcb, _hostname.empty() ? NULL : _hostname.c_str(), | ||
_root_ca, _root_ca_len) < 0; | ||
} else { | ||
err = tcp_ssl_new_psk_client(_pcb, _psk_ident, _psk) < 0; | ||
} | ||
if (err) { | ||
log_e("closing...."); | ||
return _close(); | ||
} | ||
|
||
tcp_ssl_arg(_pcb, this); | ||
tcp_ssl_data(_pcb, &_s_data); | ||
tcp_ssl_handshake(_pcb, &_s_handshake); | ||
tcp_ssl_err(_pcb, &_s_ssl_error); | ||
} | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
} | ||
#if ASYNC_TCP_SSL_ENABLED | ||
// _connect_cb happens after SSL handshake if this is a secure connection | ||
if(_connect_cb && !_pcb_secure) { | ||
_connect_cb(_connect_cb_arg, this); | ||
} | ||
#else | ||
if(_connect_cb) { | ||
_connect_cb(_connect_cb_arg, this); | ||
} | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
return ERR_OK; | ||
} | ||
|
||
void AsyncClient::_error(int8_t err) { | ||
if(_pcb){ | ||
#if ASYNC_TCP_SSL_ENABLED | ||
if(_pcb_secure){ | ||
tcp_ssl_free(_pcb); | ||
} | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
tcp_arg(_pcb, NULL); | ||
tcp_sent(_pcb, NULL); | ||
tcp_recv(_pcb, NULL); | ||
|
@@ -816,6 +925,14 @@ void AsyncClient::_error(int8_t err) { | |
} | ||
} | ||
|
||
#if ASYNC_TCP_SSL_ENABLED | ||
void AsyncClient::_ssl_error(int8_t err){ | ||
if(_error_cb) { | ||
_error_cb(_error_cb_arg, this, err+64); | ||
} | ||
} | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
|
||
//In LwIP Thread | ||
int8_t AsyncClient::_lwip_fin(tcp_pcb* pcb, int8_t err) { | ||
if(!_pcb || pcb != _pcb){ | ||
|
@@ -856,6 +973,22 @@ int8_t AsyncClient::_sent(tcp_pcb* pcb, uint16_t len) { | |
int8_t AsyncClient::_recv(tcp_pcb* pcb, pbuf* pb, int8_t err) { | ||
while(pb != NULL) { | ||
_rx_last_packet = millis(); | ||
|
||
#if ASYNC_TCP_SSL_ENABLED | ||
if(_pcb_secure){ | ||
// log_i("_recv: %d\n", pb->tot_len); | ||
int read_bytes = tcp_ssl_read(pcb, pb); | ||
if(read_bytes < 0){ | ||
if (read_bytes != MBEDTLS_ERR_SSL_PEER_CLOSE_NOTIFY) { | ||
log_e("_recv err: %d\n", read_bytes); | ||
_close(); | ||
} | ||
return ERR_BUF; // for lack of a better error value | ||
} | ||
return ERR_OK; | ||
|
||
} | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
|
||
//we should not ack before we assimilate the data | ||
_ack_pcb = true; | ||
pbuf *b = pb; | ||
|
@@ -904,6 +1037,13 @@ int8_t AsyncClient::_poll(tcp_pcb* pcb){ | |
_close(); | ||
return ERR_OK; | ||
} | ||
#if ASYNC_TCP_SSL_ENABLED | ||
if(_pcb_secure && !_handshake_done && (now - _rx_last_packet) >= 5000){ | ||
tve marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
log_w("ssl handshake timeout %d", pcb->state); | ||
_close(); | ||
return ERR_OK; | ||
} | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
// Everything is fine | ||
if(_poll_cb) { | ||
_poll_cb(_poll_cb_arg, this); | ||
|
@@ -913,7 +1053,11 @@ int8_t AsyncClient::_poll(tcp_pcb* pcb){ | |
|
||
void AsyncClient::_dns_found(struct ip_addr *ipaddr){ | ||
if(ipaddr){ | ||
#if ASYNC_TCP_SSL_ENABLED | ||
connect(IPAddress(ipaddr->u_addr.ip4.addr), _connect_port, _pcb_secure); | ||
#else | ||
connect(IPAddress(ipaddr->u_addr.ip4.addr), _connect_port); | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
} else { | ||
if(_error_cb) { | ||
_error_cb(_error_cb_arg, this, -55); | ||
|
@@ -1164,6 +1308,23 @@ int8_t AsyncClient::_s_connected(void * arg, void * pcb, int8_t err){ | |
return reinterpret_cast<AsyncClient*>(arg)->_connected(pcb, err); | ||
} | ||
|
||
#if ASYNC_TCP_SSL_ENABLED | ||
void AsyncClient::_s_data(void *arg, struct tcp_pcb *tcp, uint8_t * data, size_t len){ | ||
AsyncClient *c = reinterpret_cast<AsyncClient*>(arg); | ||
if(c->_recv_cb) c->_recv_cb(c->_recv_cb_arg, c, data, len); | ||
} | ||
|
||
void AsyncClient::_s_handshake(void *arg, struct tcp_pcb *tcp, struct tcp_ssl_pcb* ssl){ | ||
AsyncClient *c = reinterpret_cast<AsyncClient*>(arg); | ||
c->_handshake_done = true; | ||
if(c->_connect_cb) c->_connect_cb(c->_connect_cb_arg, c); | ||
} | ||
|
||
void AsyncClient::_s_ssl_error(void *arg, struct tcp_pcb *tcp, int8_t err){ | ||
reinterpret_cast<AsyncClient*>(arg)->_ssl_error(err); | ||
} | ||
#endif // ASYNC_TCP_SSL_ENABLED | ||
|
||
/* | ||
Async TCP Server | ||
*/ | ||
|
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.