"relaxmike" <michael.baudin@[EMAIL PROTECTED]
> wrote in message
news:ec34d10a-0745-494c-9446-091ea4d950a9@[EMAIL PROTECTED]
> extra_mem ()
> {
> struct array1_integer(kind=4) mydata;
> static integer(kind=4) options.0[7] = {68, 255, 0, 0, 0, 1, 0};
> mydata.data = 0B;
> _gfortran_set_options (7, (void *) &options.0);
> {
> void * D.567;
> mydata.dtype = 265;
> mydata.dim[0].lbound = 1;
> mydata.dim[0].ubound = 10;
> mydata.dim[0].stride = 1;
> [... with a "D.568 = __builtin_malloc (40);" and "D.567 = D.568;"]
> mydata.data = D.567;
> mydata.offset = -1;
> [...]
> We can see the dtype (data type ?), the lower bound 1, the upper
> bound 10 (what is stride ? what is offset) and the memory location
> is probably in mydata.data.
FX just a couple of days ago do***ented this:
http://groups.google.com/group/comp.lang.fortran/msg/a3c2275c13d8db90
The thing that makes me feel a little queasy is that gfortran
doesn't have the capability to express the stride in units
that aren't a multiple of the element size. What happens when
this is not the case?
C:\gfortran\clf\odd_str>type odd_str.f90
module odd_str
implicit none
contains
subroutine str1(x, p)
character(*), target :: x(:)
character(len(x)), pointer :: p(:)
p => x
write(*,*) x
end subroutine str1
subroutine set_ptr(x, p)
character(*), target :: x(:)
character(len(x(1:3))), pointer :: p(:)
call str1(x(:)(1:3), p)
end subroutine set_ptr
end module odd_str
program test
use ISO_C_BINDING, only: C_INTPTR_T
use odd_str
implicit none
! integer, parameter :: C_INTPTR_T = int_ptr_kind()
character(8), target :: x(8)
integer i
integer, parameter :: n = 3
type has_p3
character(n), pointer :: p(:)
end type has_p3
type(has_p3) h3
type has_p8
character(len(x)), pointer :: p(:)
end type has_p8
type(has_p8) h8
do i = 1,len(x)*size(x)
x((i+len(x)-1)/len(x))(modulo(i-1,len(x))+1:modulo(i-1,len(x))+1) &
= achar(32+i)
end do
write(*,*) x
! call str1(x(:)(1:n),h3%p)
call set_ptr(x,h3%p)
write(*,'(z16.16)') transfer(h3,[0_C_INTPTR_T])
write(*,*) h3%p
h8%p => x
write(*,'(z16.16)') transfer(h8,[0_C_INTPTR_T])
write(*,*) h8%p
end program test
C:\gfortran\clf\odd_str>gfortran odd_str.f90 -oodd_str
C:\gfortran\clf\odd_str>odd_str
!"#$%&'()*+,-./0123456789:;<=>?@[EMAIL PROTECTED]
!"#)*+1239:;ABCIJKQRSYZ[
00000000004A5A20
FFFFFFFFFFFFFFFF
00000000000000F1
0000000000000001
0000000000000001
0000000000000008
* #)*+1239:;ABCIJKQRSYZ[
000000000022FD90
FFFFFFFFFFFFFFFF
0000000000000231
0000000000000001
0000000000000001
0000000000000008
!"#$%&'()*+,-./0123456789:;<=>?@[EMAIL PROTECTED]
>rem edit for compatibility with ifort 9.1
C:\gfortran\clf\odd_str>ifort odd_str.f90
Intel(R) Fortran Compiler for Intel(R) EM64T-based applications, Version
9.1
Build 20061104
Copyright (C) 1985-2006 Intel Cor****ation. All rights reserved.
Microsoft (R) Incremental Linker Version 8.00.40310.39
Copyright (C) Microsoft Cor****ation. All rights reserved.
-out:odd_str.exe
-subsystem:console
odd_str.obj
C:\gfortran\clf\odd_str>odd_str
!"#$%&'()*+,-./0123456789:;<=>?@[EMAIL PROTECTED]
!"#)*+1239:;ABCIJKQRSYZ[
0000000000471540
0000000000000003
FFFFFFFFFFFFFFF8
0000000000000001
0000000000000001
0000000000000000
0000000000000008
0000000000000008
0000000000000001
!"#)*+1239:;ABCIJKQRSYZ[
0000000000471540
0000000000000008
FFFFFFFFFFFFFFF8
0000000000000007
0000000000000001
0000000000000000
0000000000000008
0000000000000008
0000000000000001
!"#$%&'()*+,-./0123456789:;<=>?@[EMAIL PROTECTED]
it seems that gfortran is treating x(:)(1:3) as an expression in
subroutine set_ptr, so p ends up pointing at the expression which is
out of scope by the time control reaches program test again. In
N1601.pdf, section 6.1.1 it says:
"If the parent is a variable, the substring is also a variable."
And indeed ifort 9.1 seems to point at the original address. You
need the extra level of indirection to see this issue with gfortran
because when str1 was called directly in this example the string
didn't end up getting munged. Is gfortran correct to treat
x(:)(1:3) as a variable or does it need to express strides in
bytes rather than element storage units so that it could express
a pointer to it correctly?
--
write(*,*) transfer((/17.392111325966148d0,6.5794487871554595D-85, &
6.0134700243160014d-154/),(/'x'/)); end


|