Thread: ecpg long int problem on alpha + fix

ecpg long int problem on alpha + fix

From
Adriaan Joubert
Date:
Hi,

    we had a problem on Alpha that in interfaces/ecpg/lib/typename.c we
have
HAVE_LONG_INT_64 defined, but not HAVE_LONG_LONG_INT_64. Consequently no
code is included for long ints and typename calls *abort*. I put in a
few lines that check for HAVE_LONG_INT_64 and seem to generate the right
code. I've got a new version of typename.c attached. It would be good if
Michael could review and get this into 7.1.

Cheers,

Adriaan#include "config.h"

#include <stdlib.h>
#include "ecpgtype.h"
#include "ecpglib.h"
#include "extern.h"
#include "sql3types.h"
#include "pg_type.h"

/*
 * This function is used to generate the correct type names.
 */
const char *
ECPGtype_name(enum ECPGttype typ)
{
    switch (typ)
    {
            case ECPGt_char:
            return "char";
        case ECPGt_unsigned_char:
            return "unsigned char";
        case ECPGt_short:
            return "short";
        case ECPGt_unsigned_short:
            return "unsigned short";
        case ECPGt_int:
            return "int";
        case ECPGt_unsigned_int:
            return "unsigned int";
        case ECPGt_long:
            return "long";
        case ECPGt_unsigned_long:
            return "unsigned long";
#if defined(HAVE_LONG_LONG_INT_64)
        case ECPGt_long_long:
            return "long long";
        case ECPGt_unsigned_long_long:
            return "unsigned long long";
#elif defined(HAVE_LONG_INT_64)
            case ECPGt_long_long:
                        return "long int";
                case ECPGt_unsigned_long_long:
                        return "unsigned long int";
#endif     /* HAVE_LONG_LONG_INT_64 */
        case ECPGt_float:
            return "float";
        case ECPGt_double:
            return "double";
        case ECPGt_bool:
            return "bool";
        case ECPGt_varchar:
            return "varchar";
        case ECPGt_char_variable:
            return "char";
        default:
            abort();
    }
    return NULL;
}

unsigned int
ECPGDynamicType(Oid type)
{
    switch (type)
    {
            case BOOLOID:return SQL3_BOOLEAN;    /* bool */
        case INT2OID:
            return SQL3_SMALLINT;        /* int2 */
        case INT4OID:
            return SQL3_INTEGER;/* int4 */
        case TEXTOID:
            return SQL3_CHARACTER;        /* text */
        case FLOAT4OID:
            return SQL3_REAL;    /* float4 */
        case FLOAT8OID:
            return SQL3_DOUBLE_PRECISION;        /* float8 */
        case BPCHAROID:
            return SQL3_CHARACTER;        /* bpchar */
        case VARCHAROID:
            return SQL3_CHARACTER_VARYING;        /* varchar */
        case DATEOID:
            return SQL3_DATE_TIME_TIMESTAMP;    /* date */
        case TIMEOID:
            return SQL3_DATE_TIME_TIMESTAMP;    /* time */
        case TIMESTAMPOID:
            return SQL3_DATE_TIME_TIMESTAMP;    /* datetime */
        case NUMERICOID:
            return SQL3_NUMERIC;/* numeric */
        default:
            return -type;
    }
}

Re: ecpg long int problem on alpha + fix

From
Michael Meskes
Date:
On Tue, Apr 03, 2001 at 06:32:25PM +0300, Adriaan Joubert wrote:
>     we had a problem on Alpha that in interfaces/ecpg/lib/typename.c we
> have
> HAVE_LONG_INT_64 defined, but not HAVE_LONG_LONG_INT_64. Consequently no

Sure since that means your long int and not your long long int is 64 bits.

> code is included for long ints and typename calls *abort*. I put in a
> few lines that check for HAVE_LONG_INT_64 and seem to generate the right

Why is this needed? What you do is use "long long" as variable type for 64
bits integer. But on the alpha you do not need "long long", just use "long
int" instead.

Or did I misunderstand something?

Michael

-- 
Michael Meskes
Michael@Fam-Meskes.De
Go SF 49ers! Go Rhein Fire!
Use Debian GNU/Linux! Use PostgreSQL!


Re: ecpg long int problem on alpha + fix

From
Michael Meskes
Date:
On Wed, Apr 04, 2001 at 03:35:34PM +0300, Adriaan Joubert wrote:
> OK, I see. Problem is that without the fix ecpg aborts when writing to a
> table with an int8 column using valid code.

Sorry, I still don't seem to understand that. Data between ecpg and the
backend is tranfered in ascii only. What exactly happens?

> all exist on alpha and are all 64 bits, but HAVE_LONG_LONG_INT_64 is not
> defined, so ecpg cannot handle ECPGt_long_long types. It is not clear to

I see. I was under the impression that HAVE_LONG_LONG_INT_64 should be
defined if long long int is 64 bit integer which of course it is on the
alpha.

> me what the best thing is to fix here -- possibly configure needs to set
> HAVE_LONG_LONG_INT_64 (which solves the problem on alpha as well), but I
> do not know what the consequences of that are.

I would think that this is the correct solution. After all there is a
#ifdef HAVE_LONG_LONG_INT_64 in the backend as well.

Anyone else with more knowledge about HAVE_LONG_LONG_INT_64 dare to comment?

Michael
-- 
Michael Meskes
Michael@Fam-Meskes.De
Go SF 49ers! Go Rhein Fire!
Use Debian GNU/Linux! Use PostgreSQL!


Re: ecpg long int problem on alpha + fix

From
Tom Lane
Date:
Michael Meskes <meskes@postgresql.org> writes:
>> all exist on alpha and are all 64 bits, but HAVE_LONG_LONG_INT_64 is not
>> defined, so ecpg cannot handle ECPGt_long_long types. It is not clear to

> I see. I was under the impression that HAVE_LONG_LONG_INT_64 should be
> defined if long long int is 64 bit integer which of course it is on the
> alpha.

No!  Look at the configure test!  It doesn't bother to investigate long
long int if it finds that long int will serve.  At most one of the two
symbols will be defined.  I believe that that is the correct way, at
least for the backend's purposes, since we only want to compile one set
of int64-related code.
        regards, tom lane


Re: ecpg long int problem on alpha + fix

From
Adriaan Joubert
Date:
Michael Meskes wrote:
> 
> On Wed, Apr 04, 2001 at 03:35:34PM +0300, Adriaan Joubert wrote:
> > OK, I see. Problem is that without the fix ecpg aborts when writing to a
> > table with an int8 column using valid code.
> 
> Sorry, I still don't seem to understand that. Data between ecpg and the
> backend is tranfered in ascii only. What exactly happens?

This has nothing to do with the backend. ecpg itself core-dumps after
calling abort() at the end of the switch statement in typename.c, when
processing a .pgc file. As people complained to me about ecpg
core-dumping I tried to find out why and then found that it called the
abort() at the end of this switch ;-)

I have not looked at ecpg in any detail, but I expect that the types in
typename.c are derived from the host variables in some way. If we have
an int8 column in a table, we need to use a 64 bit type, i.e. a 'long
long', and as HAVE_LONG_LONG_INT_64 is not true, no such type is
compiled into the switch. As HAVE_LONG_INT_64 is defined on alpha, my
fix fixes this for alpha, and any other platform where HAVE_LONG_INT_64
is defined but not HAVE_LONG_LONG_INT_64. 

From Tom's mail I gather that it is not an option to define
HAVE_LONG_LONG_INT_64 on alpha, so I think this patch, or something
similar, is necessary.

Apologies for not being clear enough initially.

Cheers,

Adriaan


Re: ecpg long int problem on alpha + fix

From
Michael Meskes
Date:
On Wed, Apr 04, 2001 at 05:47:50PM +0300, Adriaan Joubert wrote:
> This has nothing to do with the backend. ecpg itself core-dumps after
> calling abort() at the end of the switch statement in typename.c, when
> processing a .pgc file. As people complained to me about ecpg

Yes, I did understand that. What I do not understand is the problem with
long long int. On an alpha the normal long int should be sufficient for
storing int8.

> core-dumping I tried to find out why and then found that it called the
> abort() at the end of this switch ;-)

This abort() is used to make sure ecpg stops if a type id is found that does
not exist. Normally this must not happen. Ah, now I understand, the parser
accepts long long but typename.c does not like that.

It should be sufficient to just remove the #ifdef in typename.c since
nothing serious is happening there. The reason for this precompiler define
is to make sure that no long long code is generated that the C compiler
cannot cope with. But in typename.c there is no code generated other than
the creation of a string.

Could you please try to just remove the cpp flag? Also I wonder why you are
using "long long int" instead of just "long int" in your C program. Well
that is the people who complained to you.

> an int8 column in a table, we need to use a 64 bit type, i.e. a 'long
> long', and as HAVE_LONG_LONG_INT_64 is not true, no such type is

I thought "long int" is 64 bits too, so that should be sufficient.

> From Tom's mail I gather that it is not an option to define
> HAVE_LONG_LONG_INT_64 on alpha, so I think this patch, or something
> similar, is necessary.

Thanks to Tom btw for setting this straight.

> Apologies for not being clear enough initially.

I think you were pretty clear from teh get go, but I simply misunderstood
you.

Michael
-- 
Michael Meskes
Michael@Fam-Meskes.De
Go SF 49ers! Go Rhein Fire!
Use Debian GNU/Linux! Use PostgreSQL!


Re: ecpg long int problem on alpha + fix

From
Adriaan Joubert
Date:
> Could you please try to just remove the cpp flag? Also I wonder why you are
> using "long long int" instead of just "long int" in your C program. Well
> that is the people who complained to you.

Yes, dropping the CPP flags solves the problem for us. I assume all
platforms have long long now?

We used long long as this seems to be pretty consistently 64 bits on
different platforms, and our code runs on Tru64, PC linux and openBSD.
It also agrees with the CORBA type naming for 64 bit ints, so it makes
the type naming more consistent. 

Thanks,

Adriaan


Re: ecpg long int problem on alpha + fix

From
Tom Lane
Date:
Adriaan Joubert <a.joubert@albourne.com> writes:
> Yes, dropping the CPP flags solves the problem for us. I assume all
> platforms have long long now?

Surely you jest.
        regards, tom lane


Re: ecpg long int problem on alpha + fix

From
Adriaan Joubert
Date:
Tom Lane wrote:
> 
> Adriaan Joubert <a.joubert@albourne.com> writes:
> > Yes, dropping the CPP flags solves the problem for us. I assume all
> > platforms have long long now?
> 
> Surely you jest.

Yep, it was a rhetorical question. 

I think we probably do need the CPP defines from my patch in there, so
that it really doesn't work on platforms that do not have int8. But I do
not know the ins-and-outs of the ecpg code, so that's Michael's call. As
long as it works on my shiny alpha-boxes at the end of it all I'm happy
;-)

Adriaan


Re: ecpg long int problem on alpha + fix

From
Michael Meskes
Date:
On Thu, Apr 05, 2001 at 09:13:49AM +0300, Adriaan Joubert wrote:
> I think we probably do need the CPP defines from my patch in there, so

Not exactly. The test in typename.c does not make sense at all. It will be
removed. But there are other places where it is needed. Or can I safely
assume that if HAVE_LONG_INT_64 is defined then HAVE_LONG_LONG_INT_64 also
is true, although not defined?

Hmm, thinking about it, how about using long instead of long long if
HAVE_LONG_LONG_INT_64 is undefined?

Michael
-- 
Michael Meskes
Michael@Fam-Meskes.De
Go SF 49ers! Go Rhein Fire!
Use Debian GNU/Linux! Use PostgreSQL!


Re: ecpg long int problem on alpha + fix

From
Adriaan Joubert
Date:
Michael Meskes wrote:
> 
> On Tue, Apr 03, 2001 at 06:32:25PM +0300, Adriaan Joubert wrote:
> >       we had a problem on Alpha that in interfaces/ecpg/lib/typename.c we
> > have
> > HAVE_LONG_INT_64 defined, but not HAVE_LONG_LONG_INT_64. Consequently no
> 
> Sure since that means your long int and not your long long int is 64 bits.
> 
> > code is included for long ints and typename calls *abort*. I put in a
> > few lines that check for HAVE_LONG_INT_64 and seem to generate the right
> 
> Why is this needed? What you do is use "long long" as variable type for 64
> bits integer. But on the alpha you do not need "long long", just use "long
> int" instead.
> 
> Or did I misunderstand something?

OK, I see. Problem is that without the fix ecpg aborts when writing to a
table with an int8 column using valid code.

long int
long long
long long int

all exist on alpha and are all 64 bits, but HAVE_LONG_LONG_INT_64 is not
defined, so ecpg cannot handle ECPGt_long_long types. It is not clear to
me what the best thing is to fix here -- possibly configure needs to set
HAVE_LONG_LONG_INT_64 (which solves the problem on alpha as well), but I
do not know what the consequences of that are.

Cheers,

Adriaan