3

I am trying to loop over all arguments passed to a Fortran program, with the number of arguments varying. Thus I made the array of strings allocatable.

However once I to start said loop, I get a segfault, if any argument is given.

Is there any problem with having an allocatable string array?

CODE:

program read_args

implicit none
character(len=999), allocatable :: args(:)
integer, allocatable :: i, nargs

nargs=command_argument_count()

if ( nargs == 0 ) then
    print*, 'err: no arguments or options'
    stop
end if

allocate(args(1:nargs))

print*, nargs, size(args(:))
do i=1,nargs
    call getarg(i,args(i))
    args(i)=trim(adjustl(args(i)))
end do

end program

The number of arguments and array size is printed, once I try to read in the argument, I get a segfault.

Compiler, gfortran - gcc , v8.3.0 on debian 10

(To avoid XY-problems: the idea is to check for option flags in the argument list as well as to get all file names which should be processed)

Results:

$ ./a.out
err: no arguments or options

$ ./a.out arg1 arg2
2  2
<Segfault>
Saxtheowl
  • 4,136
  • 5
  • 23
  • 32
FelixJN
  • 540
  • 3
  • 16
  • This indeed fixes it. I never thought that this option was even activated when not explicitly defined (i.e. `integer, allocatable :: i(:)` ). I had mixed allocatable (vectors, arrays) and scalar values on that line in the bigger program. Could you explain this further? Also I'll gladly accept this as an answer so the topic can be closed - independently of any explanations. – FelixJN Sep 23 '19 at 18:54
  • 8
    `i` is never allocated in this program. You are probably aware that intrinsic assignment to an allocatable variable causes it to be allocated to the shape/length of the expression, but the use as a DO control variable isn't intrinsic assignment so that doesn't apply. – Steve Lionel Sep 24 '19 at 00:18
  • @SteveLionel I wasn't and didn't even know a variable with `rank=0` could need allocation. Thank you for the explanation! For future readers: automatic allocation is Fortran 2003 standard. More details [here](https://stackoverflow.com/questions/42140832/automatic-array-allocation-upon-assignment-in-fortran). – FelixJN Sep 24 '19 at 11:45

1 Answers1

4

As the comments have stated, the problem in this program is the use of the unallocated variable i in the do construct, not the use of the the character array inside the construct.

We can be precise about why this use of i is problematic.

In

do i=1,nargs

we have that i is the "do variable" (Fortran 2018, 11.1.7.2). In such a do construct we know (Fortran 2018, 11.1.7.4.1) that as part of the processing of the loop:

The DO variable becomes defined with the value of the initial parameter

So, does this "definition" involve first an allocation of i?

It does not. This contrasts with the explicit allocation process as part of intrinsic assignment, say (such as with the valid nargs=command_argument_count()). This "becomes defined" is not allowed with i not allocated (Fortran 2018, 5.4.10):

An unallocated allocatable variable shall not be referenced or defined.

The definition of i is not the same process as having i the target of an intrinsic assignment with the initial parameter.

In general, having allocatable scalars such as i and nargs can be useful, but in the case of this question that doesn't appear so: removing the allocatable attribute from them doesn't change the logic. Alternatively, i can be explicitly allocated (without needing to give it a value) before the do construct is entered.

francescalus
  • 30,576
  • 16
  • 61
  • 96