You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@qpid.apache.org by gm...@apache.org on 2021/10/27 19:13:37 UTC
[qpid-dispatch] branch main updated: DISPATCH-2264: Fix for router
crash when deleting listener
This is an automated email from the ASF dual-hosted git repository.
gmurthy pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/qpid-dispatch.git
The following commit(s) were added to refs/heads/main by this push:
new cf1d3d9 DISPATCH-2264: Fix for router crash when deleting listener
cf1d3d9 is described below
commit cf1d3d9456ac400c4ee2508de39361b78f2dc30e
Author: Ganesh Murthy <gm...@apache.org>
AuthorDate: Wed Oct 27 12:07:11 2021 -0400
DISPATCH-2264: Fix for router crash when deleting listener
---
src/adaptors/http2/http2_adaptor.c | 37 +++++++++++++++++---------
tests/system_tests_http2.py | 54 ++++++++++++++++++++++++++++++++++++--
2 files changed, 77 insertions(+), 14 deletions(-)
diff --git a/src/adaptors/http2/http2_adaptor.c b/src/adaptors/http2/http2_adaptor.c
index e70c331..a3864a6 100644
--- a/src/adaptors/http2/http2_adaptor.c
+++ b/src/adaptors/http2/http2_adaptor.c
@@ -2603,9 +2603,25 @@ static void handle_listener_event(pn_event_t *e, qd_server_t *qd_server, void *c
}
break;
- case PN_LISTENER_CLOSE:
- qd_log(log, QD_LOG_INFO, "Closing HTTP connection on %s", host_port);
- break;
+ case PN_LISTENER_CLOSE: {
+ if (li->pn_listener) {
+ pn_condition_t *cond = pn_listener_condition(li->pn_listener);
+ if (pn_condition_is_set(cond)) {
+ qd_log(log, QD_LOG_ERROR, "Listener error on %s: %s (%s)", host_port, pn_condition_get_description(cond), pn_condition_get_name(cond));
+ }
+ else {
+ qd_log(log, QD_LOG_TRACE, "Listener closed on %s", host_port);
+ }
+ }
+
+ sys_mutex_lock(http2_adaptor->lock);
+ pn_listener_set_context(li->pn_listener, 0);
+ li->pn_listener = 0;
+ DEQ_REMOVE(http2_adaptor->listeners, li);
+ sys_mutex_unlock(http2_adaptor->lock);
+ qd_http_listener_decref(li);
+ }
+ break;
default:
break;
@@ -2637,18 +2653,13 @@ void qd_http2_delete_connector(qd_dispatch_t *qd, qd_http_connector_t *connector
*/
void qd_http2_delete_listener(qd_dispatch_t *qd, qd_http_listener_t *li)
{
+ sys_mutex_lock(http2_adaptor->lock);
if (li) {
if (li->pn_listener) {
pn_listener_close(li->pn_listener);
- li->pn_listener = 0;
}
- sys_mutex_lock(http2_adaptor->lock);
- DEQ_REMOVE(http2_adaptor->listeners, li);
- sys_mutex_unlock(http2_adaptor->lock);
-
- qd_log(http2_adaptor->log_source, QD_LOG_INFO, "Deleted HttpListener for %s, %s:%s", li->config.address, li->config.host, li->config.port);
- qd_http_listener_decref(li);
}
+ sys_mutex_unlock(http2_adaptor->lock);
}
@@ -2708,14 +2719,16 @@ static void qdr_http2_adaptor_final(void *adaptor_context)
// Free all http listeners
qd_http_listener_t *li = DEQ_HEAD(adaptor->listeners);
while (li) {
- qd_http2_delete_listener(0, li);
+ DEQ_REMOVE_HEAD(adaptor->listeners);
+ qd_http_listener_decref(li);
li = DEQ_HEAD(adaptor->listeners);
}
// Free all http connectors
qd_http_connector_t *ct = DEQ_HEAD(adaptor->connectors);
while (ct) {
- qd_http2_delete_connector(0, ct);
+ DEQ_REMOVE_HEAD(adaptor->connectors);
+ qd_http_connector_decref(ct);
ct = DEQ_HEAD(adaptor->connectors);
}
diff --git a/tests/system_tests_http2.py b/tests/system_tests_http2.py
index 74746c3..e373a17 100644
--- a/tests/system_tests_http2.py
+++ b/tests/system_tests_http2.py
@@ -221,6 +221,43 @@ class CommonHttp2Tests:
digest_of_response_file = get_digest(self.router_qdra.outdir + image_file_name)
self.assertEqual(digest_of_server_file, digest_of_response_file)
+ def check_listener_delete(self, client_addr, server_addr):
+ # Run curl 127.0.0.1:port --http2-prior-knowledge
+ # We are first making sure that the http request goes thru successfully.
+ out = self.run_curl(client_addr)
+ ret_string = ""
+ i = 0
+ while (i < 1000):
+ ret_string += str(i) + ","
+ i += 1
+ self.assertIn(ret_string, out)
+
+ qd_manager = QdManager(self, address=server_addr)
+ http_listeners = qd_manager.query('org.apache.qpid.dispatch.httpListener')
+ self.assertEqual(len(http_listeners), 1)
+
+ # Run a qdmanage DELETE on the httpListener
+ qd_manager.delete("org.apache.qpid.dispatch.httpListener", name=self.listener_name)
+
+ # Make sure the listener is gone
+ http_listeners = qd_manager.query('org.apache.qpid.dispatch.httpListener')
+ self.assertEqual(len(http_listeners), 0)
+
+ # Try running a curl command against the listener to make sure it times out
+ request_timed_out = False
+ try:
+ out = self.run_curl(client_addr, timeout=3)
+ except Exception as e:
+ request_timed_out = True
+ self.assertTrue(request_timed_out)
+
+ # Add back the listener and run a curl command to make sure that the newly added listener is
+ # back up and running.
+ create_result = qd_manager.create("org.apache.qpid.dispatch.httpListener", self.http_listener_props)
+ sleep(2)
+ out = self.run_curl(client_addr)
+ self.assertIn(ret_string, out)
+
def check_connector_delete(self, client_addr, server_addr):
# Run curl 127.0.0.1:port --http2-prior-knowledge
# We are first making sure that the http request goes thru successfully.
@@ -469,12 +506,20 @@ class Http2TestTwoRouter(Http2TestBase, CommonHttp2Tests):
server_file="http2_server.py")
name = "http2-test-router"
inter_router_port = cls.tester.get_port()
+ cls.http_listener_port = cls.tester.get_port()
+ cls.listener_name = 'listenerToBeDeleted'
+ cls.http_listener_props = {
+ 'port': cls.http_listener_port,
+ 'address': 'examples',
+ 'host': '127.0.0.1',
+ 'protocolVersion': 'HTTP2',
+ 'name': cls.listener_name
+ }
config_qdra = Qdrouterd.Config([
('router', {'mode': 'interior', 'id': 'QDR.A'}),
('listener', {'port': cls.tester.get_port(), 'role': 'normal', 'host': '0.0.0.0'}),
- ('httpListener', {'port': cls.tester.get_port(), 'address': 'examples',
- 'host': '127.0.0.1', 'protocolVersion': 'HTTP2'}),
+ ('httpListener', cls.http_listener_props),
('listener', {'role': 'inter-router', 'port': inter_router_port})
])
@@ -554,6 +599,11 @@ class Http2TestTwoRouter(Http2TestBase, CommonHttp2Tests):
self.assertEqual(stats_b[0].get('bytesIn'), 3944)
@unittest.skipIf(skip_test(), "Python 3.7 or greater, Quart 0.13.0 or greater and curl needed to run http2 tests")
+ def test_yyy_http_listener_delete(self):
+ self.check_listener_delete(client_addr=self.router_qdra.http_addresses[0],
+ server_addr=self.router_qdra.addresses[0])
+
+ @unittest.skipIf(skip_test(), "Python 3.7 or greater, Quart 0.13.0 or greater and curl needed to run http2 tests")
def test_zzz_http_connector_delete(self):
self.check_connector_delete(client_addr=self.router_qdra.http_addresses[0],
server_addr=self.router_qdrb.addresses[0])
---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@qpid.apache.org
For additional commands, e-mail: commits-help@qpid.apache.org