Thread: snprintf()

snprintf()

From
Kate F
Date:
Hello,

I've been implementing a type I needed, and happened to be using
snprintf(), since I have C99 available.
ereport(NOTICE,    (errcode(ERRCODE_NUMERIC_VALUE_OUT_OF_RANGE),    errmsg("%d", snprintf(NULL, 0, "abc"))));

For me, this reports "0". I beieve it should report 3. My system's
snprintf() returns 3. I'm using NetBSD. By including postgres.h and
fmgr.h, does PostgreSQL replace my system's snprintf() prototype with
its own implementation's?

Placing stdio.h above those includes appears to have no effect.

For reference, the relevant part of C99:
 7.19.6.5 2 If n is zero, nothing is written, and s may be a null pointer.
 7.19.6.5 3 The snprintf function returns the number of characters that would have been written had n been sufficiently
large,not counting the terminating null character, or a neg ative value if an encoding error occurred.
 

Regards,

-- 
Kate


Re: snprintf()

From
Tom Lane
Date:
Kate F <kate@cats.meow.at> writes:
> ... does PostgreSQL replace my system's snprintf() prototype with
> its own implementation's?

We do on some platforms where configure decides the system version
is deficient ... I don't recall the exact conditions at the moment.
I wouldn't really have expected that to happen on any *BSD, but you
could look into the generated Makefile.global to find out.

> For reference, the relevant part of C99:
>   7.19.6.5 2 If n is zero, nothing is written, and s may be a null
>   pointer.

For reference, the relevant part of the Single Unix Spec:
If the value of n is zero on a call to snprintf(), anunspecified value less than 1 is returned.

So the behavior you'd like to depend on is unportable anyway, and
that coding will get rejected if submitted as a Postgres patch.
        regards, tom lane


Re: snprintf()

From
Kate F
Date:
On Fri, Feb/ 2/07 10:52:28PM -0500, Tom Lane wrote:
> Kate F <kate@cats.meow.at> writes:
> > ... does PostgreSQL replace my system's snprintf() prototype with
> > its own implementation's?
> 
> We do on some platforms where configure decides the system version
> is deficient ... I don't recall the exact conditions at the moment.
> I wouldn't really have expected that to happen on any *BSD, but you
> could look into the generated Makefile.global to find out.

I don't see anything that looks relevant for my Makefile.global; I
would be surprised if NetBSD's were overridden too!


> > For reference, the relevant part of C99:
> >   7.19.6.5 2 If n is zero, nothing is written, and s may be a null
> >   pointer.
> 
> For reference, the relevant part of the Single Unix Spec:
> 
>     If the value of n is zero on a call to snprintf(), an
>     unspecified value less than 1 is returned.

Aha! I do recall either POSIX or SUS defers to C on conflicts... I
can't find which, though. If this snprintf() is following SUS
behaviour, that's fine. Thank you!


> So the behavior you'd like to depend on is unportable anyway, and
> that coding will get rejected if submitted as a Postgres patch.

Absolutley (and I assume you target C89, too, which does not provide
snprintf()). This was just something personal where I happened to use
it for convenience.

Thank you for checking that - and appologies for posting to the wrong
list; that should have been to -bugs!

Regards,

-- 
Kate


Re: snprintf()

From
Tom Lane
Date:
Kate F <kate@cats.meow.at> writes:
> On Fri, Feb/ 2/07 10:52:28PM -0500, Tom Lane wrote:
>> I wouldn't really have expected that to happen on any *BSD, but you
>> could look into the generated Makefile.global to find out.

> I don't see anything that looks relevant for my Makefile.global; I
> would be surprised if NetBSD's were overridden too!

Sorry for not being specific: the thing to check is whether that
file's definition for LIBOBJS includes snprintf.o.  If it does,
the code in src/port/snprintf.c would get sucked in.

If it doesn't, then I confess bafflement as to why snprintf isn't
acting as you'd expect on your machine.
        regards, tom lane


Re: snprintf()

From
Kate F
Date:
On Fri, Feb/ 2/07 11:20:07PM -0500, Tom Lane wrote:
> Kate F <kate@cats.meow.at> writes:
> > On Fri, Feb/ 2/07 10:52:28PM -0500, Tom Lane wrote:
> >> I wouldn't really have expected that to happen on any *BSD, but you
> >> could look into the generated Makefile.global to find out.
> 
> > I don't see anything that looks relevant for my Makefile.global; I
> > would be surprised if NetBSD's were overridden too!
> 
> Sorry for not being specific: the thing to check is whether that
> file's definition for LIBOBJS includes snprintf.o.  If it does,
> the code in src/port/snprintf.c would get sucked in.
> 
> If it doesn't, then I confess bafflement as to why snprintf isn't
> acting as you'd expect on your machine.

Just these:

LIBOBJS =  copydir.o dirmod.o exec.o noblock.o path.o pipe.o pgsleep.opgstrcasecmp.o qsort.o qsort_arg.o sprompt.o
thread.o

(More than I expected, actually)

I am imagining the compiler (gcc, here) has some flags to explicitly
select if C99 (which is what I tested my stand-alone example with)
or SUS behaviour is to be used. I'm not really sure how I'd set that,
though - I imagine I'd need to recompile the backend with -std=C99?

Regards,

-- 
Kate