Silverfrost Forums

Welcome to our forums

Returning string to .NET in parameters...

29 Sep 2009 12:09 #5069

Hi, I have a function that takes 17 string parameters, and returns string values in the last 7. In Fortran they are output parameters and I can write into them with null terminated strings, but using the /CLR option to use them in C# they are given a type of 'string' in the generated DLL signature. In .NET the string type is immutable, so the program obviously can't modify them. Referring to non-managed DLLs requires that stringbuilders be used to allow the interface layer to modify them, but how do I get the return values in Fortran.net? The examples on disk only use basic number types, so they don't help me much.

Thanks, Norm.

29 Sep 2009 12:26 #5070

Have you looked at the help file under .NET Platform->.NET Programming->.NET string type?

29 Sep 2009 12:38 #5071

Yes, and I don't see anything about using the strings for output values. The documentation says that every string as passed as though through a C# 'ref' parameter, but unless this is specified in the DLL's signature there is no way the destination compiled Fortran.NET can modify the value.

How do you receive the modified value of a string parameter, or is this not possible in the current version?

Cheers, Norm

29 Sep 2009 1:02 #5072

.NET objects are passed by reference so this may provide a way to work. Alternatively you may be able to use character arrays rather than strings. Note that arrays are passed by reference.

29 Sep 2009 1:21 #5073

Yes, but strings are immutable. For example, this does NOT work:

    class Program
    {
        static void Main(string[] args)
        {
            string s = 'hello';
            DoSomething(s);
            Console.WriteLine(s);
        }

        private static void DoSomething(string s)
        {
            s = 'Now I'm Fred';
        }
    }

but this DOES work:

    class Program
    {
        static void Main(string[] args)
        {
            string s = 'hello';
            DoSomething(ref s);
            Console.WriteLine(s);
        }

        private static void DoSomething(ref string s)
        {
            s = 'Now I'm Fred';
        }
    }

Note that the 'ref' keyword must be specified on both ends of the call! The FTN95 signature has no ref defined, so does this mean the /CLR is wrongly ignoring the fact that the parameter is marked as OUTPUT, preventing us from returning values this way, or is there some way to tell the compiler to honour the signature properly for the .NET framework?

Cheers, Norm

29 Sep 2009 1:31 #5074

The help file says that strings are passed by value but I am suggesting that you convert your strings to arrays of characters so that they are passed by reference.

1 Oct 2009 9:15 #5095

Hi Paul,

Have you tried this? In .Net you can change the contents of an object passed by reference, but only if that object in turn has references to its contents (such as properties in an object), so the only way to override this is to use the 'ref' keyword on a parameter.

Here is an identical example using a char array (which also does not work):

    class Program
    {
        static void Main(string[] args)
        {
            char[] s = 'hello'.ToCharArray();
            DoSomething(s);
            Console.WriteLine(s);
        }

        private static void DoSomething(char[] s)
        {
            s = 'Now I'm Fred'.ToCharArray();
        }
    }

The FTN95 compiler produces the equivalent of the above 'DoSomething' function, but there is no way to modify the parameter without 'ref', as this is a fundamental part of the .NET runtime. What I'm asking is if there is any way to make the compiler correctly generate the parameters by reference, otherwise it seems impossible to handle Fortran's OUTPUT parameters.

Cheers, Norm

1 Oct 2009 10:34 #5097

Before I try this for myself can you just check that, in your Fortran, a .NET character array with the attribute INTENT(OUT) is not coded as a ref.

Please login to reply.