Passing parameters to a C function

Started by Rodrigo Sakaialmost 19 years ago3 messageshackers
Jump to latest
#1Rodrigo Sakai
rodrigo.sakai@poli.usp.br

Hello,

I have a question about passing parameters to a C function. Imagine the
example by PostgreSQL:

PG_FUNCTION_INFO_V1(complex_add);

Datum

complex_add(PG_FUNCTION_ARGS)

{

Complex *a = (Complex *) PG_GETARG_POINTER(0);

Complex *b = (Complex *) PG_GETARG_POINTER(1);

Complex *result;

result = (Complex *) palloc(sizeof(Complex));

result->x = a->x + b->x;

result->y = a->y + b->y;

PG_RETURN_POINTER(result);

}

So, in the same .C file I have to write another function that calls this
one, for example:

void

test_main()

{

Complex *a;

Complex *b;

a = complex_in("(4.01, 3.77 )");

printf("a = %s\n", complex_out(a));

b = complex_in("(1.0,2.0)");

printf("b = %s\n", complex_out(b));

printf("a + b = %s\n", complex_out(complex_add(a,b)));

}

But using version 1 calling convention it won't work! So, how can I pass the
'a' and 'b' variables in complex_add(?, ?)?

Thanks in advance!

#2Martijn van Oosterhout
kleptog@svana.org
In reply to: Rodrigo Sakai (#1)
Re: Passing parameters to a C function

On Wed, May 30, 2007 at 11:26:01AM -0300, Rodrigo Sakai wrote:

I have a question about passing parameters to a C function. Imagine the
example by PostgreSQL:

PG_FUNCTION_INFO_V1(complex_add);

But using version 1 calling convention it won't work! So, how can I pass the
'a' and 'b' variables in complex_add(?, ?)?

Use the DirectFunctionCalln functions in fmgr.

Have a nice day,
--
Martijn van Oosterhout <kleptog@svana.org> http://svana.org/kleptog/

Show quoted text

From each according to his ability. To each according to his ability to litigate.

#3Tom Lane
tgl@sss.pgh.pa.us
In reply to: Martijn van Oosterhout (#2)
Re: Passing parameters to a C function

Martijn van Oosterhout <kleptog@svana.org> writes:

On Wed, May 30, 2007 at 11:26:01AM -0300, Rodrigo Sakai wrote:

But using version 1 calling convention it won't work! So, how can I pass the
'a' and 'b' variables in complex_add(?, ?)?

Use the DirectFunctionCalln functions in fmgr.

There are boatloads of examples in the existing datatype code, for
instance this function in geo_ops.c, which is just applying
close_sb() followed by dist_pb():

Datum
dist_sb(PG_FUNCTION_ARGS)
{
LSEG *lseg = PG_GETARG_LSEG_P(0);
BOX *box = PG_GETARG_BOX_P(1);
Point *tmp;
Datum result;

tmp = DatumGetPointP(DirectFunctionCall2(close_sb,
LsegPGetDatum(lseg),
BoxPGetDatum(box)));
result = DirectFunctionCall2(dist_pb,
PointPGetDatum(tmp),
BoxPGetDatum(box));

PG_RETURN_DATUM(result);
}

All that casting to and from Datum is a bit of a pain, but it's worth it
to have a uniform, portable function API.

I strongly suggest adding some appropriate cast macros for your own
datatype, like the ones being used here, instead of dealing directly
with low-level operations like PG_GETARG_POINTER.

regards, tom lane