Re: BUG? select count(*) from table don't get value via PQgetvalue() function in libpq(C)

From: Tom Lane <tgl(at)sss(dot)pgh(dot)pa(dot)us>
To: "Gao Yanxiao" <553216793(at)qq(dot)com>
Cc: pgsql-bugs(at)postgresql(dot)org
Subject: Re: BUG? select count(*) from table don't get value via PQgetvalue() function in libpq(C)
Date: 2017-02-18 17:58:28
Message-ID: 27458.1487440708@sss.pgh.pa.us
Views: Raw Message | Whole Thread | Download mbox | Resend email
Thread:
Lists: pgsql-bugs

"Gao Yanxiao" <553216793(at)qq(dot)com> writes:
> res = PQexecParams(pgconn, "select count(*) from chat_connstate", 0, NULL, NULL, NULL, NULL, 1);

So you asked for binary-format results ...

> So, I use PQgetvalue() function get the value, like this:
> Int result = *((int*)PQgetvalue(res, 0, 0));
> Or
> Long result = *((long*)PQgetvalue(res, 0, 0);

The first of those is certainly not going to work, and depending on what
platform you're on the second won't either, because it's only extracting
the first 32 bits of the 64-bit result of count().

The other problem you've got here is that the result is coming off the
wire in big-endian byte order, and you're not doing anything to convert
that into native byte order (which more than likely is little-endian).
The reason you're seeing zeroes is that the high 32 bits of the result
are zeroes.

Personally, I would not bother with binary format unless I anticipated
processing enormous volumes of data; it's just too error-prone.
Better to use text and apply strtol() or whatever.

If you really must do it in binary format, here's the way pq_getmsgint64
reads a 64-bit big-endian value:

int64 result;
uint32 h32;
uint32 l32;

pq_copymsgbytes(msg, (char *) &h32, 4);
pq_copymsgbytes(msg, (char *) &l32, 4);
h32 = ntohl(h32);
l32 = ntohl(l32);

result = h32;
result <<= 32;
result |= l32;

which is pretty tedious, but there's no standard 64-bit version
of ntohl/htonl, so we have to swap each half separately.

regards, tom lane

In response to

Browse pgsql-bugs by date

  From Date Subject
Next Message Stefan Stefanov 2017-02-19 16:41:09 Re: BUG #14549: pl/pgsql parser
Previous Message Gao Yanxiao 2017-02-18 16:04:08 BUG? select count(*) from table don't get value via PQgetvalue() function in libpq(C)