VALUE attribute not working with IVFC XE 2013 SP1

VALUE attribute not working with IVFC XE 2013 SP1

Hi

We updated Intel Visual Fortran Composer XE 2011 to XE 2013 SP1 and Visual Studio 2008 to 2010 Premium.

It seems that the VALUE attribute is not working anymore and it's not recognized as a special word in Visual Studio.

Here's small sample:

Fuction specification:

integer(4) function csta_sect_num(selected, mode)
	use, intrinsic :: ISO_C_BINDING
	use CSE_STA_USER

	IMPLICIT NONE
	
	LOGICAL(C_BOOL), VALUE, intent(in)	:: selected
	integer(C_INT), optional, intent(in)	:: mode
...

Interface:

interface csta_sect_num
	function csta_sect_num (selected, mode) result (num)
		use, intrinsic :: ISO_C_BINDING
		implicit none
		logical(C_BOOL), VALUE, intent(in)    :: selected
		integer(C_INT), optional, intent(in)  :: mode
		integer(C_INT)                        :: num
	end function csta_sect_num
end interface csta_sect_num

C++ declaration:

extern "C" int csta_sect_num (bool selected, int * mode = 0);

C++ function call:

bool sel = false;
int num = csta_sect_num(sel);

The selected argument gets passed by reference and will crash the program.

If I add

BIND(C,NAME='csta_sect_num')

to the function definition and to its interface, it will work, or if I add the

!DIR$ ATTRIBUTES VALUE :: selected

compiler directive to the parameter, it will also work.

Shouldn't the VALUE attribute work also without neither of these additions?

br

Janne

5 posts / 0 new
Last post
For more complete information about compiler optimizations, see our Optimization Notice.

You need BIND(C) on the declaration of the routine in Fortran. But my guess is that you also have /standard-semantics enabled.

We had incorrectly implemented VALUE - without BIND(C), it does NOT mean pass-by-value. We left the default behavior the old one, but if you asked for Fortran 2003 semantics, you get the standard-required behavior (which is to pass an anonymous copy by reference.)

Retired 12/31/2016

Hi Steve and thanks for your answer!

The Fortran 2003 semantics is turned on.

If BIND(C) is used, the routine works when called from Fortran and from C++. From C++'s point of view, it's still kind of by value, right? What I mean is that the Fortran compiler magically makes things work when the routine is called by value from C++ which is exactly what we want. :)

- Janne

 

There's no magic involved.

If the procedure has the BIND(C) attribute, specifying VALUE means pass and receive by value. If you call a Fortran routine declared this way, the compiler is supposed to make a definable copy of the dummy argument.

If the procedure does NOT have BIND(C) but the argument has VALUE, then the effect is that a definable copy is passed by reference.

We mis-implemented this many years ago so that the standard VALUE attribute was treated exactly like ATTRIBUTES VALUE. For 14.0, we fixed this, but for various reasons made it not the default behavior. To get the standard behavior, you need to specify /assume:std-value or /standard-semantics. In a future release we may make the standard behavior the default.

You probably want BIND(C) on the routine interface so you get pass-by-value from either Fortran or C++.

Retired 12/31/2016

OK, thanks for the clarification. This makes sense. The good thing is that BIND(C) works also when called from Fortran and we don't need to make two different versions of the same function for C++ and Fortran callers.

- Janne

 

Leave a Comment

Please sign in to add a comment. Not a member? Join today