Skip to content

Commit 23ed1e4

Browse files
matias-martiniMatias Martini
andauthored
Fix dangling pointer after client.close (#527)
* Test(client): Add dead test after closing client We recently encountered an unexpected Segmentation Fault Error when checking whether a client was dead after closing it. To consider this in the future, I've updated the test cases for the client to include this scenario, so we can catch any issues earlier on. * Fix(client) Set dangling pointer to NULL after client closure We recently encountered an unexpected Segmentation Fault Error while checking if a client was dead after closing it. Upon investigation, we discovered that the issue was caused by deallocating all memory used by the client structure without setting the pointer to NULL after closing the client connection through dbclose. This resulted in a dangling pointer, which led to the Segmentation Fault when we tried to check whether the client was dead using TDS dbdead. To prevent this issue from occurring again, I have made the necessary updates to set the client pointer to NULL after every dbclose. This will ensure that we avoid any dangling pointers and keep our code running smoothly. --------- Co-authored-by: Matias Martini <[email protected]>
1 parent 12a2e45 commit 23ed1e4

File tree

3 files changed

+4
-0
lines changed

3 files changed

+4
-0
lines changed

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
## (unreleased)
22

33
* Add Ruby 3.0 to the cross compile list
4+
* Fix segfault when asking if client was dead after closing it. Fixes #519.
45

56
## 2.1.5
67

ext/tiny_tds/client.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -232,6 +232,7 @@ static void rb_tinytds_client_free(void *ptr) {
232232
dbloginfree(cwrap->login);
233233
if (cwrap->client && !cwrap->closed) {
234234
dbclose(cwrap->client);
235+
cwrap->client = NULL;
235236
cwrap->closed = 1;
236237
cwrap->userdata->closed = 1;
237238
}
@@ -263,6 +264,7 @@ static VALUE rb_tinytds_close(VALUE self) {
263264
GET_CLIENT_WRAPPER(self);
264265
if (cwrap->client && !cwrap->closed) {
265266
dbclose(cwrap->client);
267+
cwrap->client = NULL;
266268
cwrap->closed = 1;
267269
cwrap->userdata->closed = 1;
268270
}

test/client_test.rb

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ class ClientTest < TinyTds::TestCase
1616
assert @client.close
1717
assert @client.closed?
1818
assert !@client.active?
19+
assert @client.dead?
1920
action = lambda { @client.execute('SELECT 1 as [one]').each }
2021
assert_raise_tinytds_error(action) do |e|
2122
assert_match %r{closed connection}i, e.message, 'ignore if non-english test run'

0 commit comments

Comments
 (0)