Skip to content

Commit ff8dc1d

Browse files
committed
Don't call $sth->finish() when InactiveDestroy is set
DBI already calls dbd_st_finish() before dbd_st_destroy() if the handle is active. For inactive handles no finish() should be necessary. With InactiveDestroy set, the handle is always considered inactive. Skipping finish() could lead to "out of sync" situations and inconsistencies, however, the attribute is explicitly meant to skip all DB-related destroy actions, especially for the case when the connection will be closed anyway. The only thing which is not cleaned up by finish() is the last result. This commit fixes the following example: $dbh->{'AutoInactiveDestroy'} = 1; my $sth = $dbh->prepare('SELECT id FROM bcwb_maint_types; SELECT SLEEP(1); SELECT text FROM bcwb_maint_types;'); $sth->execute(); my $i = 0; do { printf "Result %d\n", ++$i; while (my $id = $sth->fetchrow_array()) { print $id, "\n"; } print "---\n"; if ($i == 1) { if (my $pid = fork()) { waitpid($pid, 0); } else { exit(0); } } } while ($sth->more_results);
1 parent b1f4834 commit ff8dc1d

File tree

1 file changed

+2
-7
lines changed

1 file changed

+2
-7
lines changed

dbdimp.c

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -5441,13 +5441,8 @@ void mariadb_st_destroy(SV *sth, imp_sth_t *imp_sth) {
54415441
int num_params;
54425442
int num_fields;
54435443

5444-
if (!PL_dirty)
5445-
{
5446-
/* During global destruction, DBI objects are destroyed in random order
5447-
* and therefore imp_dbh may be already freed. So do not access it. */
5448-
mariadb_st_finish(sth, imp_sth);
5449-
mariadb_st_free_result_sets(sth, imp_sth, TRUE);
5450-
}
5444+
if (imp_sth->result)
5445+
mysql_free_result(imp_sth->result);
54515446

54525447
DBIc_ACTIVE_off(imp_sth);
54535448

0 commit comments

Comments
 (0)