|
forums.silverfrost.com Welcome to the Silverfrost forums
|
View previous topic :: View next topic |
Author |
Message |
simon
Joined: 05 Jul 2006 Posts: 268
|
Posted: Wed Feb 15, 2017 11:17 pm Post subject: Pointers and intent |
|
|
The following program creates a window with a menu item and a button, both of which call the same callback function, f, which is defined in module m. The call-back function allocates memory to two arrays, x and y, that are defined as pointers. It then tries to call a subroutine, s, which declares the arrays as Intent(Out) rather than as pointers (I think that is legal, but I am not certain), but only one of the arrays is actually assigned any values.
If you click on the menu item the program runs, but it hangs if you click on the button. FTN95 does not typically seem to complain if an Intent(Out) argument is left unassigned, and this problem only seems to occur if the callback function is activated from a window.
Any suggestions? I suppose the place to start is to confirm whether or not the coding is valid Fortran. Change the arguments in the subroutine to pointers and the problem disappears. However, if I make an equivalent change to my original 70,000 line program the problem is not resolved. And since it took me 3 working days to isolate the problem below, I'm hoping that diagnosing what might be happening with this small program will help fix my larger program!
Code: | Module m
!
Real, Dimension(:), Pointer :: x => Null()
Real, Dimension(:), Pointer :: y => Null()
!
Contains
!
Function f()
Integer :: f
!
Allocate (x(2))
Allocate (y(2))
Print *, 'Call s2'
Call s (x, y)
Print *, 'Called S2'
f = 2
Return
End Function f
!
!
Subroutine s (x, y)
Real, Dimension(:), Intent(Out) :: x, y
!
Print *, 'Start'
x(:) = 1.0
Print *, 'End'
Return
End Subroutine s
End Module m
!
!
Winapp
Program cpt
!
Use clrwin, Only: winio@
Use m, Only: f
!
Integer :: ic_par ! - parent window control variable -
Integer :: iw ! - window argument -
Integer :: ih_con ! - ClearWin+ window handle -
!
! Open test window
iw = winio@('%ca@&', 'TEST')
iw = winio@('%mn[test]&', f)
iw = winio@('%cn%^5tt@%ff&', 'test', f)
iw = winio@('%ff %`50.10cw&', 0, ih_con)
iw = winio@('%lw', ic_par)
!
End Program cpt
|
|
|
Back to top |
|
|
simon
Joined: 05 Jul 2006 Posts: 268
|
Posted: Thu Feb 16, 2017 2:45 am Post subject: |
|
|
... I forgot to add that I have some reason for suspecting that the problem may only occur on Windows 10, but I'm unable to test that assertion. |
|
Back to top |
|
|
PaulLaidler Site Admin
Joined: 21 Feb 2005 Posts: 7928 Location: Salford, UK
|
Posted: Sat Feb 18, 2017 11:03 am Post subject: |
|
|
It looks like FTN95 is not able to pass x from f to s in this way.
It might be a programming error or a bug in FTN95.
It would be simpler to declare x (and y) as "allocatable" rather than as "pointer". This seems to work may be valid Fortran.
The fact that it "works" in 64 bit mode is interesting and may give a clue to what is going wrong. |
|
Back to top |
|
|
simon
Joined: 05 Jul 2006 Posts: 268
|
Posted: Thu Feb 23, 2017 1:25 am Post subject: |
|
|
I agree it would be easier to declare x and y as allocatable rather than as pointers, but if x and y are allocated in s rather than in f, they can only be passed as arguments in Fortran 95 if they are pointers. I think at Fortran 2003 they can be passed as allocatable arguments, but FTN95 does not allow that. I would like to do something like the following, but it is not possible in FTN95. My Fortran 2008 compiler allows it.
Code: | Module m
!
Real, Dimension(:), Allocatable :: x
Real, Dimension(:), Allocatable :: y
!
Contains
!
Subroutine s (x, y)
Real, Dimension(:), Allocatable :: x, y
!
Allocate (x(2))
Allocate (y(2))
Return
End Subroutine s
End Module m
!
!
Program p
Use m
!
Call s(x, y)
Print *, Allocated (x), Allocated (y)
End Program p |
|
|
Back to top |
|
|
PaulLaidler Site Admin
Joined: 21 Feb 2005 Posts: 7928 Location: Salford, UK
|
Posted: Thu Feb 23, 2017 9:28 am Post subject: |
|
|
Thanks for this. It is on the list of things to investigate. |
|
Back to top |
|
|
JohnCampbell
Joined: 16 Feb 2006 Posts: 2554 Location: Sydney
|
Posted: Fri Feb 24, 2017 9:09 am Post subject: |
|
|
simon,
for your latest example, Silverfrost FTN95 does not support allocatable arguments, which is an F95 addition.
Try the following alternative, by referencing the allocatable arrays through the module. This is required for FTN95 to manage allocatable arrays, although F03 can do what you want, (without using modules)
( I actually don't understand the use of contains + the use of arguments that are already in scope. I may be missing some of your example )
Code: | Module m
!
Real, Dimension(:), Allocatable :: x
Real, Dimension(:), Allocatable :: y
!
Contains
!
Subroutine s ! remove arguments (x, y)
! Real, Dimension(:), Allocatable :: x, y
!
Allocate (x(2))
Allocate (y(2))
Return
End Subroutine s
End Module m
!
!
Program p
Use m
!
Call s ! remove arguments (x, y)
Print *, Allocated (x), Allocated (y)
End Program p |
|
|
Back to top |
|
|
simon
Joined: 05 Jul 2006 Posts: 268
|
Posted: Fri Feb 24, 2017 11:53 pm Post subject: |
|
|
Thanks for the suggestion John. I've been considering that, but ideally I'd like s to be a generic routine, so that I can call it to assign memory to a variety of arrays - hence the preference to have them passed as arguments. Using pointers seems to be the only way to do that in Fortran95, but I was getting an unexpected error when running from ClearWin+, as my original posting indicates.
Regarding the Contains + routines with arguments that are declared in the module in the same, there were two considerations here:
1. Having the routine arguments allows arrays to be passed that were not originally from that module;
2. Having arguments allows the user to allocate a selection of the arrays.
I presented the example in this manner primarily to keep the example program as short as possible. But also, I suppose I prefer to avoid having routines that modify values that are not arguments (except perhaps for workspace) so that there are no unexpected changes; although that does sometimes make for long argument lists. |
|
Back to top |
|
|
JohnCampbell
Joined: 16 Feb 2006 Posts: 2554 Location: Sydney
|
Posted: Sat Feb 25, 2017 1:47 am Post subject: |
|
|
Quote: | Regarding the Contains + routines with arguments |
I suspect I may be proved wrong, but I think this is a coding error. Subroutine S should not be contained.
You should use /xref to check what x and y you are using; the argument or the module arrays.
John |
|
Back to top |
|
|
simon
Joined: 05 Jul 2006 Posts: 268
|
Posted: Wed Mar 01, 2017 3:36 pm Post subject: |
|
|
I seem to have inadvertently introduced a separate issue with the subroutine taking arguments that are declared in the same module. My original concern was about an apparent problem with a pointer being given an intent, but not consistently causing the program to hang. If this problem is a result of an illegal use of intent on a pointer, than that would be good to know, but I will have to go back and look more carefully at my larger program, since changing the offending intents back to pointers has not solved the problem.
Meanwhile, to illustrate the problem without introducing confouding issues around subroutine arguments, if I put X and Y in a separate module, the following program still hangs if I click on browse, but not if I click on the menu item.
Code: | ! This program hangs if the button is selected but not the menu item
Module m1
!
Real, Dimension(:), Pointer :: x => Null()
Real, Dimension(:), Pointer :: y => Null()
!
End Module m1
!
!
Module m2
!
Contains
!
Function f()
Use m1
Integer :: f
!
Allocate (x(2))
Allocate (y(2))
Print *, 'Call s'
Call s (x, y)
Print *, 'Called s'
f = 2
Return
End Function f
!
!
Subroutine s (x, y)
Real, Dimension(:), Intent(Out) :: x, y
!
Print *, 'Start'
x(:) = 1.0
Print *, 'End'
Return
End Subroutine s
End Module m2
!
!
Winapp
Program cpt
!
Use clrwin, Only: winio@
Use m2, Only: f
!
Integer :: ic_par ! - parent window control variable -
Integer :: iw ! - window argument -
Integer :: ih_con ! - ClearWin+ window handle -
!
! Open test window
iw = winio@('%ca@&', 'TEST')
iw = winio@('%mn[test]&', f)
iw = winio@('%cn%^5tt@%ff&', 'test', f)
iw = winio@('%ff %`50.10cw&', 0, ih_con)
iw = winio@('%lw', ic_par)
!
End Program cpt |
|
|
Back to top |
|
|
JohnCampbell
Joined: 16 Feb 2006 Posts: 2554 Location: Sydney
|
Posted: Thu Mar 02, 2017 12:48 am Post subject: |
|
|
Simon,
I compiled your latest example in Plato and it ran using either menu or button.
I am using FTN95 Ver 8.05.0
buildlog is:
FTN95.EXE "C:\temp\forum\simon2.f90" /NO_BANNER /VS7 /DELETE_OBJ_ON_ERROR /ERROR_NUMBERS /UNLIMITED_ERRORS /LINK /CHECKMATE
FTN95 /64 gave an error with the kind of ih_con, even when declaring integer(7) ih_con
This was eventually corrected with ftn95 ver 8.10.0
Your example does not hang with 8.xx
John
Code: | ! This program hangs if the button is selected but not the menu item
Module m1
!
Real, Dimension(:), Pointer :: x => Null()
Real, Dimension(:), Pointer :: y => Null()
integer :: num = 0
!
End Module m1
!
!
Module m2
!
Contains
!
Function f()
Use m1
Integer :: f
!
num = num+1
Allocate (x(20000000))
Allocate (y(20000000))
Print *, 'Call s', num
Call s (x, y)
Print *, 'Called s'
f = 2
Return
End Function f
!
!
Subroutine s (x, y)
Real, Dimension(:), Intent(Out) :: x, y
!
Print *, 'Start'
x(:) = 1.0
Print *, 'End'
Return
End Subroutine s
End Module m2
!
!
Winapp
Program cpt
!
Use clrwin, Only: winio@
Use m2, Only: f
!
Integer :: iw ! - window argument -
Integer(7) :: ih_con ! - ClearWin+ window handle -
Integer :: ic_par ! - parent window control variable -
!
! Open test window
iw = winio@('%ca@&', 'TEST')
iw = winio@('%mn[test]&', f)
iw = winio@('%cn%^5tt@%ff&', 'test', f)
iw = winio@('%ff %`50.10cw&', 0, ih_con)
iw = winio@('%lw', ic_par)
!
End Program cpt |
You should run this example in task manager, clicking test multiple times, as it demonstrates the memory leakage problem with pointers, as X and Y are not deallocated. I much prefer Allocatable arrays. |
|
Back to top |
|
|
simon
Joined: 05 Jul 2006 Posts: 268
|
Posted: Thu Mar 02, 2017 2:39 am Post subject: |
|
|
Hi John,
Are you running on Windows 10? It doesn;t work on Windows 10, neither does my larger program, but my larger program does run on earlier versions of Windows. |
|
Back to top |
|
|
JohnCampbell
Joined: 16 Feb 2006 Posts: 2554 Location: Sydney
|
Posted: Thu Mar 02, 2017 4:20 am Post subject: |
|
|
Simon,
Yes !! I did to the test on Windows 7. My 3 other PC's are Windows 10, so I shall do the test soon.
I don't know why I changed from Win 7. The list of Win 10 improvements is fairly short. It's newer; not much more !!
Back to your origan post : I don't have much experience of pointers, as I try to avoid them. I find allocatable arrays in modules to be much more robust. I also rarely use INTENT=as it has little practical benefit in my type of coding.
John |
|
Back to top |
|
|
JohnCampbell
Joined: 16 Feb 2006 Posts: 2554 Location: Sydney
|
Posted: Fri Mar 03, 2017 12:32 am Post subject: |
|
|
Paul,
Has there been any investigation of the work required to implement TR_15581:1999 ?
It has three main types of allocatable attributes:
• array components of structures,
• dummy arrays, and
• array function results
The inclusion of Allocatable arrays as Dummy Arguments has been a useful extension to F95 for managing allocatable arrays, as Simon has shown in this thread.
I am not aware of the work required for this extension, so would be interested in your comments.
John |
|
Back to top |
|
|
PaulLaidler Site Admin
Joined: 21 Feb 2005 Posts: 7928 Location: Salford, UK
|
Posted: Fri Mar 03, 2017 8:32 am Post subject: |
|
|
John
I don't know for sure but I doubt it. Perhaps this will come apparent when we come to investigate this issue. |
|
Back to top |
|
|
PaulLaidler Site Admin
Joined: 21 Feb 2005 Posts: 7928 Location: Salford, UK
|
Posted: Wed Feb 13, 2019 7:36 pm Post subject: |
|
|
Simon
This old issue does not appear to have been resolved.
Now, on going back to it, I am unable to reproduce the fault.
This suggests to me that there was something in Windows 10 that has now been fixed. |
|
Back to top |
|
|
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum
|
Powered by phpBB © 2001, 2005 phpBB Group
|