Calling C from Fortran
(Forgot to post.) Yes, that was a typo, and the reason is the same; the C
function expects a value rather than its address. That's why you can't use
it directly from Fortran (aside from naming issues) but it's fine in C.
Reid Huntsinger
-----Original Message-----
From: Gilles GUILLOT [mailto:gilles.guillot at inapg.inra.fr]
Sent: Wednesday, June 15, 2005 11:50 AM
To: R-devel at lists.R-project.org
Cc: Huntsinger, Reid
Subject: Re: [Rd] Calling C from Fortran
Thanks for your reply.
Am I write if I say that the wrapper shoul be
double F77_SUB(mygammafn)(double *x) { return gammafn(*x); }
instead of
double F77_SUB(mygammafn)(double *x) { return gammafn(x); }
the first does not compile.
wrapper2.c: In function `mygammafn_':
wrapper2.c:6: error: incompatible type for argument 1 of `Rf_gammafn'
The second compiles and works fine.
But still, I find it very strange as the C function gammafn actually called
( as I can see from /R-2.1.0/src/nmath/gamma.c)
is not defined as
double gammafn(double *x)
but as
double gammafn(double x)
Am I missing something ?
Gilles
Le Mercredi 15 Juin 2005 17:06, vous avez ?crit :
I actually deleted a part of my reply, dealing with exactly that. Sorry!
You need to declare the C wrapper to take a pointer to a double ("double
*") rather than a double. C passes by value whereas Fortran passes by
reference; in C you get this effect by passing a pointer to the value
(which is also a value). So you want
double F77_SUB(mygammafn)(double *x) { return gammafn(x); }
That should work; if not let me know and I'll look more carefully at
Fortran <-> C conventions.
Reid Huntsinger
-----Original Message-----
From: Gilles GUILLOT [mailto:gilles.guillot at inapg.inra.fr]
Sent: Wednesday, June 15, 2005 3:50 AM
To: Huntsinger, Reid
Subject: Re: [Rd] Calling C from Fortran
Thanks Reid!
And now if I want to call a C function with arguments,
e.g. to compute the gamma function at x,
my C wrapper is:
#include <R.h>
#include <Rmath.h>
void F77_SUB(rndstart)(void) { GetRNGstate(); }
void F77_SUB(rndend)(void) { PutRNGstate(); }
double F77_SUB(normrnd)(void) { return norm_rand(); }
double F77_SUB(mygammafn)(double x) { return gammafn(x); }
And my Fortran is:
subroutine testit()
implicit none
double precision normrnd, x, y, mygammafn
call rndstart()
x = dabs(normrnd())
write(*,*) 'x=',x
call rndend()
y = mygammafn(x)
write(*,*) 'y=',y
end
And it does not work, all calls of testit return the same y value.
What is incorrect in my files ?
Gilles
---------------------------------------------------------------------------
--- Notice: This e-mail message, together with any attachments, contains information of Merck & Co., Inc. (One Merck Drive, Whitehouse Station, New Jersey, USA 08889), and/or its affiliates (which may be known outside the United States as Merck Frosst, Merck Sharp & Dohme or MSD and in Japan, as Banyu) that may be confidential, proprietary copyrighted and/or legally privileged. It is intended solely for the use of the individual or entity named on this message. If you are not the intended recipient, and have received this message in error, please notify us immediately by reply e-mail and then delete it from your system.
---------------------------------------------------------------------------
---
_________________________________________________________________________ Gilles GUILLOT INRA -D?partement Math?matiques et Informatique Appliqu?es Unit? Mixte de Recherche INRA - INAPG - ENGREF Institut National Agronomique de Paris-Grignon 16, rue Claude Bernard 75231 Paris cedex 5 France phone 33 1 44 08 18 42 fax 33 1 44 08 16 66 http://www.inapg.fr/ens_rech/mathinfo/personnel/guillot/welcome.html