|
From: Jeremy C. <je...@co...> - 2006-01-12 07:29:12
|
I am running my program through Valgrind and found that the combination
of libdbi and the pgsql dbi driver causes a memory leak when performing
a SELECT query that returns no results. The area that is leaking is in
relation to _dbd_result_set_numfields in dbd_helper.c ... These items
are allocated presumably when the result actually has a row count. In
dbd_pgsql.c, around like 450, I find:
if (!res || ((resstatus != PGRES_COMMAND_OK) && (resstatus !=
PGRES_TUPLES_OK))) {
PQclear(res);
return NULL;
}
result = _dbd_result_create(conn, (void *)res, (unsigned long
long)PQntuples(res), (unsigned long long)atoll(PQcmdTuples(res)));
_dbd_result_set_numfields(result, (unsigned int)PQnfields((PGresult
*)result->result_handle));
_get_field_info(result);
The if statement is the problem (I believe). It is possible to have a
result and PGRES_TUPLES_OK when there are no rows. Then, we come down a
few lines later and setup the field information. This is nice, that we
can retrieve field information on queries that return zero results. I
use that myself for some code generation off of database queries.
I believe the actual problem lies in dbi_result.c, around like 539:
if (result->numfields) {
As seen above, PostgreSQL set's the numfields to zero, yet it does fill
in the result->field_names, result->field_types, result->field_attribs
that are free'd inside this if statement.
I *hacked* the if statement above to read:
if (result->numfields || result->field_names != NULL) {
and all my memory leaks disappeared. Now, the reason I say hacked is
obvious. This is not a clean solution to the problem and I have no clue
what kind of side effects this will have on the postgresql driver, let
alone the other libdbi drivers that I have not used.
Any thoughts?
Jeremy Cowgar
|