postgres 9.0 beta libpq empty binary array error - Mailing list pgsql-bugs

From
Subject postgres 9.0 beta libpq empty binary array error
Date
Msg-id ACD5CA75ACCCFA4599E033DD674453037AE5AADD6D@mail2a.alliedtesting.com
Whole thread Raw
Responses Re: postgres 9.0 beta libpq empty binary array error  (Tom Lane <tgl@sss.pgh.pa.us>)
List pgsql-bugs
Hi,

I'm using libpq PQexecParams ability to send query parameters as binary dat=
a,=20
more specific - a binary representation of an empty array.

I have the problem:=20
the code sending empty binary array works on 8.3 and 8.4=20
but stopped working on postgres 9.0 beta2/3/4, it fails with '22003','integ=
er out of range error'.

Here is the test code:

char *command=3D"INSERT INTO test.arraytypes(nullarr) VALUES($1)";
//              ndims hassnull typeid ((dim+lbound)*ndims)
const int empty_array_length =3D 4 + 4 + 4 + (8*1);

// constructing empty array representation:
char * buf =3D (char *)malloc(empty_array_length);
memset(buf,0,empty_array_length);
char * out =3D buf;
// ndims
*((int*)out) =3D htonl(1);
out+=3D4;
// hassnull
*((int*)out) =3D 0;
out+=3D4;
// typeid 'int4'
*((int*)out) =3D htonl(23);
out+=3D4;

const Oid oids[] =3D {1007};// _int4 oid
const int paramFormats[]=3D{1};
const int lens[] =3D {empty_array_length};
const char * const * vals =3D {&buf};
PGresult* re =3D PQexecParams(conn, command, 1, oids,
    (const char *const * ) vals, lens, paramFormats, 1);

char *err1=3DPQresultErrorMessage(re); // ERROR:  integer out of range for =
9.0 beta


// sql creation code:
//CREATE TABLE test.arraytypes( nullarr int[])



I've traced the error down to array_recv function, and found this overflow =
check to be offending.
/src/backend/utils/adt/arrayfuncs.c:  Line 1214

for (i =3D 0; i < ndim; i++)
    {
    int            ub;
    dim[i] =3D pq_getmsgint(buf, 4);
    lBound[i] =3D pq_getmsgint(buf, 4);
    ub =3D lBound[i] + dim[i] - 1;

    /* overflow? */
    if (lBound[i] > ub)
        ereport(ERROR,
                (errcode(ERRCODE_NUMERIC_VALUE_OUT_OF_RANGE),
                 errmsg("integer out of range")));
}

In the empty array case, the ndim=3D=3D1, and dim[0]=3D=3D0, so lBound[0] >=
 ub[0]

Seems that the overflow check was introduced fairly recently, here is the d=
iscussion of it:
http://archives.postgresql.org/pgsql-hackers/2009-08/msg02073.php

The array with dim[i] =3D 0 seems legitimate, since this situation is handl=
ed by the code below:
if (nitems =3D=3D 0)
{
    /* Return empty array ... but not till we've validated element_type */
    PG_RETURN_ARRAYTYPE_P(construct_empty_array(element_type));
}

So, is it really a bug in 9.0? Or maybe the array representation rules chan=
ged somehow?

Vladimir Shakhov | Developer
www.alliedtesting.com

pgsql-bugs by date:

Previous
From: Heikki Linnakangas
Date:
Subject: Assertion failure with assignment to array elem
Next
From: Tom Lane
Date:
Subject: Re: postgres 9.0 beta libpq empty binary array error