Skip to content

Commit bea2210

Browse files
committed
CDRIVER-721 mongoc_client_destroy crash after connection fails
Undo two bad changes introduced while fixing CDRIVER-695, and add another safety check in _mongoc_cluster_node_destroy.
1 parent 95421cb commit bea2210

File tree

2 files changed

+59
-7
lines changed

2 files changed

+59
-7
lines changed

src/mongoc/mongoc-cluster.c

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -320,7 +320,6 @@ _mongoc_cluster_node_destroy (mongoc_cluster_node_t *node)
320320
ENTRY;
321321

322322
ALWAYS_ASSERT(node);
323-
ALWAYS_ASSERT(node->valid);
324323

325324
if (node->stream) {
326325
mongoc_stream_close(node->stream);
@@ -572,9 +571,12 @@ _mongoc_cluster_destroy (mongoc_cluster_t *cluster) /* INOUT */
572571

573572
mongoc_uri_destroy (cluster->uri);
574573

575-
for (i = 0; i < cluster->nodes_len; i++) {
576-
if (cluster->nodes[i].stream) {
577-
_mongoc_cluster_node_destroy (&cluster->nodes [i]);
574+
/* nodes should never be NULL if nodes_len > 0, but check anyway */
575+
if (cluster->nodes) {
576+
for (i = 0; i < cluster->nodes_len; i++) {
577+
if (cluster->nodes[i].stream) {
578+
_mongoc_cluster_node_destroy (&cluster->nodes[i]);
579+
}
578580
}
579581
}
580582

@@ -2094,8 +2096,8 @@ _mongoc_cluster_reconnect_replica_set (mongoc_cluster_t *cluster,
20942096
mongoc_list_t *liter;
20952097
int32_t ping;
20962098
const char *replSet;
2097-
int i;
2098-
int j;
2099+
uint32_t i;
2100+
uint32_t j;
20992101
bool rval = false;
21002102

21012103
ENTRY;
@@ -2205,6 +2207,7 @@ _mongoc_cluster_reconnect_replica_set (mongoc_cluster_t *cluster,
22052207
/* reinitialize nodes with same length as peer list. */
22062208
for (liter = list, i = 0; liter; liter = liter->next, i++) {}
22072209
cluster->nodes = bson_realloc (cluster->nodes, sizeof (*cluster->nodes) * i);
2210+
cluster->nodes_len = i;
22082211

22092212
for (j = 0; j < i; j++) {
22102213
_mongoc_cluster_node_init (&cluster->nodes[j]);
@@ -2284,7 +2287,7 @@ _mongoc_cluster_reconnect_replica_set (mongoc_cluster_t *cluster,
22842287

22852288
cluster->nodes[i].valid = true;
22862289
i++;
2287-
cluster->nodes_len = (uint32_t) i;
2290+
cluster->nodes_len = i;
22882291
}
22892292

22902293
_mongoc_list_foreach(list, (void(*)(void*,void*))bson_free, NULL);

tests/test-mongoc-client.c

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -455,6 +455,54 @@ test_mongoc_client_preselect (void)
455455
}
456456

457457

458+
static void
459+
test_unavailable_seeds(void)
460+
{
461+
mongoc_client_t *client;
462+
mongoc_collection_t *collection;
463+
mongoc_cursor_t *cursor;
464+
bson_t query = BSON_INITIALIZER;
465+
const bson_t *doc;
466+
467+
const char* uri_strs[] = {
468+
"mongodb://a:1/?connectTimeoutMS=1",
469+
"mongodb://a:1,a:2/?connectTimeoutMS=1",
470+
"mongodb://a:1,a:2/?replicaSet=r&connectTimeoutMS=1",
471+
"mongodb://u:p@a:1/?connectTimeoutMS=1",
472+
"mongodb://u:p@a:1,a:2/?connectTimeoutMS=1",
473+
"mongodb://u:p@a:1,a:2/?replicaSet=r&connectTimeoutMS=1",
474+
};
475+
476+
int i;
477+
478+
/* hardcode the number of error messages we have to suppress */
479+
for (i = 0; i < 18; i++) {
480+
suppress_one_message ();
481+
}
482+
483+
for (i = 0; i < (sizeof(uri_strs) / sizeof(const char *)); i++) {
484+
client = mongoc_client_new (uri_strs[i]);
485+
assert (client);
486+
487+
collection = mongoc_client_get_collection (client, "test", "test");
488+
cursor = mongoc_collection_find (collection,
489+
MONGOC_QUERY_NONE,
490+
0,
491+
0,
492+
0,
493+
&query,
494+
NULL,
495+
NULL);
496+
497+
assert (! mongoc_cursor_next (cursor, &doc));
498+
499+
mongoc_cursor_destroy (cursor);
500+
mongoc_collection_destroy (collection);
501+
mongoc_client_destroy (client);
502+
}
503+
}
504+
505+
458506
static void
459507
test_exhaust_cursor (void)
460508
{
@@ -693,6 +741,7 @@ test_client_install (TestSuite *suite)
693741
TestSuite_Add (suite, "/Client/command", test_mongoc_client_command);
694742
TestSuite_Add (suite, "/Client/command_secondary", test_mongoc_client_command_secondary);
695743
TestSuite_Add (suite, "/Client/preselect", test_mongoc_client_preselect);
744+
TestSuite_Add (suite, "/Client/unavailable_seeds", test_unavailable_seeds);
696745
TestSuite_Add (suite, "/Client/exhaust_cursor", test_exhaust_cursor);
697746
TestSuite_Add (suite, "/Client/server_status", test_server_status);
698747
}

0 commit comments

Comments
 (0)