You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@qpid.apache.org by as...@apache.org on 2019/07/12 20:04:16 UTC
[qpid-proton] 03/04: PROTON-1473: Better behaviour if peer
disconnects in the middle of header exchange - Especially if the server
disconnects the client because of authentication failure There is no more
spurious 'Header mismatch' error.
This is an automated email from the ASF dual-hosted git repository.
astitcher pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/qpid-proton.git
commit 45dba0047dab66465e011a0b65d21af670772aa3
Author: Andrew Stitcher <as...@apache.org>
AuthorDate: Mon Jul 1 18:42:10 2019 -0400
PROTON-1473: Better behaviour if peer disconnects in the middle of header exchange
- Especially if the server disconnects the client because of authentication failure
There is no more spurious 'Header mismatch' error.
---
c/src/core/transport.c | 12 +++++++++---
c/src/sasl/sasl.c | 9 ++++++++-
c/src/ssl/openssl.c | 5 ++++-
python/tests/proton_tests/engine.py | 2 +-
4 files changed, 22 insertions(+), 6 deletions(-)
diff --git a/c/src/core/transport.c b/c/src/core/transport.c
index 50bce64..9caa79d 100644
--- a/c/src/core/transport.c
+++ b/c/src/core/transport.c
@@ -274,7 +274,7 @@ ssize_t pn_io_layer_input_autodetect(pn_transport_t *transport, unsigned int lay
const char* error;
bool eos = transport->tail_closed;
if (eos && available==0) {
- pn_do_error(transport, "amqp:connection:framing-error", "No valid protocol header found");
+ pn_do_error(transport, "amqp:connection:framing-error", "No protocol header found (connection aborted)");
pn_set_error_layer(transport);
return PN_EOS;
}
@@ -1848,7 +1848,7 @@ static ssize_t transport_consume(pn_transport_t *transport)
// flow to the app the same way, but provides cleaner error messages
// since we don't try to look for a protocol header when, e.g. the
// connection was refused.
- if (!transport->bytes_input && transport->tail_closed &&
+ if (!(transport->present_layers & LAYER_AMQP1) && transport->tail_closed &&
pn_condition_is_set(&transport->condition)) {
pn_do_error(transport, NULL, NULL);
return PN_EOS;
@@ -2577,9 +2577,15 @@ static void pn_error_amqp(pn_transport_t* transport, unsigned int layer)
static ssize_t pn_input_read_amqp_header(pn_transport_t* transport, unsigned int layer, const char* bytes, size_t available)
{
bool eos = transport->tail_closed;
+ if (eos && available==0) {
+ pn_do_error(transport, "amqp:connection:framing-error",
+ "Expected AMQP protocol header: no protocol header found (connection aborted)");
+ return PN_EOS;
+ }
pni_protocol_type_t protocol = pni_sniff_header(bytes, available);
switch (protocol) {
case PNI_PROTOCOL_AMQP1:
+ transport->present_layers |= LAYER_AMQP1;
if (transport->io_layers[layer] == &amqp_read_header_layer) {
transport->io_layers[layer] = &amqp_layer;
} else {
@@ -2597,7 +2603,7 @@ static ssize_t pn_input_read_amqp_header(pn_transport_t* transport, unsigned int
char quoted[1024];
pn_quote_data(quoted, 1024, bytes, available);
pn_do_error(transport, "amqp:connection:framing-error",
- "%s header mismatch: %s ['%s']%s", "AMQP", pni_protocol_name(protocol), quoted,
+ "Expected AMQP protocol header got: %s ['%s']%s", pni_protocol_name(protocol), quoted,
!eos ? "" : " (connection aborted)");
return PN_EOS;
}
diff --git a/c/src/sasl/sasl.c b/c/src/sasl/sasl.c
index 3b257ab..454877e 100644
--- a/c/src/sasl/sasl.c
+++ b/c/src/sasl/sasl.c
@@ -542,9 +542,16 @@ static void pn_error_sasl(pn_transport_t* transport, unsigned int layer)
static ssize_t pn_input_read_sasl_header(pn_transport_t* transport, unsigned int layer, const char* bytes, size_t available)
{
bool eos = transport->tail_closed;
+ if (eos && available==0) {
+ pn_do_error(transport, "amqp:connection:framing-error",
+ "Expected SASL protocol header: no protocol header found (connection aborted)");
+ pn_set_error_layer(transport);
+ return PN_EOS;
+ }
pni_protocol_type_t protocol = pni_sniff_header(bytes, available);
switch (protocol) {
case PNI_PROTOCOL_AMQP_SASL:
+ transport->present_layers |= LAYER_AMQPSASL;
if (transport->io_layers[layer] == &sasl_read_header_layer) {
transport->io_layers[layer] = &sasl_layer;
} else {
@@ -563,7 +570,7 @@ static ssize_t pn_input_read_sasl_header(pn_transport_t* transport, unsigned int
char quoted[1024];
pn_quote_data(quoted, 1024, bytes, available);
pn_do_error(transport, "amqp:connection:framing-error",
- "%s header mismatch: %s ['%s']%s", "SASL", pni_protocol_name(protocol), quoted,
+ "Expected SASL protocol header got: %s ['%s']%s", pni_protocol_name(protocol), quoted,
!eos ? "" : " (connection aborted)");
pn_set_error_layer(transport);
return PN_EOS;
diff --git a/c/src/ssl/openssl.c b/c/src/ssl/openssl.c
index 4adf630..8e325a6 100644
--- a/c/src/ssl/openssl.c
+++ b/c/src/ssl/openssl.c
@@ -1012,7 +1012,10 @@ static int start_ssl_shutdown(pn_transport_t *transport)
static ssize_t process_input_ssl( pn_transport_t *transport, unsigned int layer, const char *input_data, size_t available)
{
pni_ssl_t *ssl = transport->ssl;
- if (ssl->ssl == NULL && init_ssl_socket(transport, ssl, NULL)) return PN_EOS;
+ if (ssl->ssl == NULL) {
+ if (init_ssl_socket(transport, ssl, NULL)) return PN_EOS;
+ transport->present_layers |= LAYER_SSL;
+ }
ssl_log( transport, "process_input_ssl( data size=%d )",available );
diff --git a/python/tests/proton_tests/engine.py b/python/tests/proton_tests/engine.py
index 41857c2..3736cbc 100644
--- a/python/tests/proton_tests/engine.py
+++ b/python/tests/proton_tests/engine.py
@@ -2453,7 +2453,7 @@ class EventTest(CollectorTest):
self.expect(Event.TRANSPORT_ERROR, Event.TRANSPORT_TAIL_CLOSED)
assert t.condition is not None
assert t.condition.name == "amqp:connection:framing-error"
- assert "AMQP header mismatch" in t.condition.description
+ assert "AMQP protocol header" in t.condition.description
p = t.pending()
assert p > 0
t.pop(p)
---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@qpid.apache.org
For additional commands, e-mail: commits-help@qpid.apache.org