• Why I can't read from a parameter string? [was: is there a better way t

    From Ev. Drikos@21:1/5 to Ev. Drikos on Sun Jun 19 13:05:29 2022
    On 15/06/2022 13:04, Ev. Drikos wrote:
    On 13/06/2022 01:46, Lynn McGuire wrote:
    So, is there a better way to code this ?


    Better no, maybe more compact. If performance is an
    issue one can declare ie the string as a parameter.
    ...

    Admittedly, maintaining a packed array is likely more
    difficult than a usual array of integers but i thought
    that this wouldn't be a big problem for an experienced
    programmer. Now, I focus to another problem i faced.

    To my surprise, if one defined the packed array as a
    parameter, the following statement would become invalid:

    icep.f:20:1:
    read(goes(icep:icep),*) nn
    ^
    Expression at (^) has incorrect data type or rank for its context

    Does anybody know why there is such a restriction?


    ----------------------------------------------
    $ gfc --version 2>&1 | head -n1
    GNU Fortran (GCC 3.2.2 20030222 (Red Hat Linux 3.2.2-5)) 3.2.2 20030222
    (Red Hat Linux 3.2.2-5)
    $ gfc icep.f && ./a.out
    11: goes=2

    $
    --------------- icep.f -------------------------------
    ! CHECK THE COMMANDS WHICH SHOULD HAVE EQUAL SIGN
    ! 10 - no equal sign required
    ! 11 - equal sign required

    integer :: icep = 302 !ie
    integer :: nn
    character(350) :: goes = &
    & '12121212121212121212121212121212121212121211212121'
    & !001-050 21-70
    & // '12121212121212121212121212121212121212121211212121'
    & !051-100 21-70
    & // '12121212121212121212121212121212121212121211212121'
    & !101-150 21-70
    & // '12121212121212121212121212121212121212121211212121'
    & !151-200 21-70
    & // '12121212121212121212121212121212121212121211212121'
    & !201-250 21-70
    & // '12121212121212121212121212121212121212121211212121'
    & !251-300 21-70
    & // '12121212121212121212121212121212121212121212121212'
    !301-350 21-70
    ! __20 25 30 35 40 45 50 55 60 65 70__
    ! cells col. !234567890123456789012345678901234567890123456789012345678901234567890xx

    read(goes(icep:icep),*) nn
    goto(10,11) nn

    10 print *, '10: ', 'goes=', goes(icep:icep)
    goto 999
    11 print *, '11: ', 'goes=', goes(icep:icep)
    goto 999
    999 end

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Thomas Koenig@21:1/5 to Ev. Drikos on Sun Jun 19 10:12:44 2022
    Ev. Drikos <drikosev@gmail.com> schrieb:

    Does anybody know why there is such a restriction?


    ----------------------------------------------
    $ gfc --version 2>&1 | head -n1
    GNU Fortran (GCC 3.2.2 20030222 (Red Hat Linux 3.2.2-5)) 3.2.2 20030222
    (Red Hat Linux 3.2.2-5)

    Without looking at the code: g77 has not been maintained for a really
    long time, and it only implements f77 + some extensions. I would not
    be surprised by any restrictions of anything f90-like or later.

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Ev. Drikos@21:1/5 to Thomas Koenig on Sun Jun 19 13:21:58 2022
    On 19/06/2022 13:12, Thomas Koenig wrote:
    Ev. Drikos <drikosev@gmail.com> schrieb:

    Does anybody know why there is such a restriction?


    ----------------------------------------------
    $ gfc --version 2>&1 | head -n1
    GNU Fortran (GCC 3.2.2 20030222 (Red Hat Linux 3.2.2-5)) 3.2.2 20030222
    (Red Hat Linux 3.2.2-5)

    Without looking at the code: g77 has not been maintained for a really
    long time, and it only implements f77 + some extensions. I would not
    be surprised by any restrictions of anything f90-like or later.


    Thanks for the feedback, the OP discussed F77. In this case version 8
    issues a similar error as well:

    $ gfortran8 -ffixed-form icep.f
    icep.f:20:11:

    read(goes(icep:icep),*) nn
    1
    Error: UNIT specification at (1) must be an INTEGER expression or a
    CHARACTER variable

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Ev. Drikos@21:1/5 to Ev. Drikos on Sun Jun 19 16:49:37 2022
    On 19/06/2022 13:21, Ev. Drikos wrote:
    ...

    $ gfortran8 -ffixed-form icep.f
    icep.f:20:11:

           read(goes(icep:icep),*) nn
               1
    Error: UNIT specification at (1) must be an INTEGER expression or a
    CHARACTER variable


    Ok, an extra assignment to a variable could solve this issue, ie:

    ch = go(icep:icep) !an extra assignment to a variable
    read(ch, *) nn
    goto(10,11) nn

    Due to the fixed form format, the example is readable in my gists: https://gist.github.com/drikosev/7f24acb6435f441d5d6f7be220efdbe9

    Yet, the question remains open. Is it perhaps a compiler specific bug
    or a standard restriction?

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Thomas Koenig@21:1/5 to Ev. Drikos on Sun Jun 19 14:17:36 2022
    Ev. Drikos <drikosev@gmail.com> schrieb:
    On 19/06/2022 13:12, Thomas Koenig wrote:
    Ev. Drikos <drikosev@gmail.com> schrieb:

    Does anybody know why there is such a restriction?


    ----------------------------------------------
    $ gfc --version 2>&1 | head -n1
    GNU Fortran (GCC 3.2.2 20030222 (Red Hat Linux 3.2.2-5)) 3.2.2 20030222
    (Red Hat Linux 3.2.2-5)

    Without looking at the code: g77 has not been maintained for a really
    long time, and it only implements f77 + some extensions. I would not
    be surprised by any restrictions of anything f90-like or later.


    Thanks for the feedback, the OP discussed F77. In this case version 8
    issues a similar error as well:

    $ gfortran8 -ffixed-form icep.f
    icep.f:20:11:

    read(goes(icep:icep),*) nn
    1
    Error: UNIT specification at (1) must be an INTEGER expression or a
    CHARACTER variable

    OK.

    A look at the F2018 standard tells us, in 12.4, "Internal Files":

    An internal file is a record file with the following properties.

    • The file is a variable of default, ASCII, or ISO 10646 character
    kind that is not an array section with a vector subscript.

    and a bit further down

    R1201 io-unit is file-unit-number
    or *
    or internal-file-variable

    R1203 internal-file-variable is char-variable

    and further up

    R905 char-variable is variable
    C905 (R905) char-variable shall be of type character.

    and finally

    R903 variable-name is name
    C903 (R903) variable-name shall be the name of a variable.

    And if anybody wonders what a variable is, it's defined in

    3.154 variable
    data entity that can be defined and redefined during execution of a program

    So, since a parameter cannot be redefined during execution, using
    an internal I/O statement on it is an error, and the processor
    needs to be able to diagnose it.

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Ron Shepard@21:1/5 to Ev. Drikos on Sun Jun 19 09:48:53 2022
    On 6/19/22 8:49 AM, Ev. Drikos wrote:
    On 19/06/2022 13:21, Ev. Drikos wrote:
    ...

    $ gfortran8 -ffixed-form icep.f
    icep.f:20:11:

            read(goes(icep:icep),*) nn
                1
    Error: UNIT specification at (1) must be an INTEGER expression or a
    CHARACTER variable


    Ok, an extra assignment to a variable could solve this issue, ie:

     ch = go(icep:icep) !an extra assignment to a variable
     read(ch, *) nn
     goto(10,11) nn

    Due to the fixed form format, the example is readable in my gists: https://gist.github.com/drikosev/7f24acb6435f441d5d6f7be220efdbe9

    Yet, the question remains open. Is it perhaps a compiler specific bug
    or a standard restriction?

    It is a standard restriction in f77. I remember similar situations many
    times in the 1980s.

    12.2.5.1 Internal File Properties. An internal file has the following properties:
    (1) The file is a character variable, character array element, character
    array, or character substring.

    Most compiler writers interpreted that to mean that it could not be
    either a literal or a parameter constant. I seem to recall there were
    some exceptions, but I always took those exceptions as extensions to the standard, so if portability was important, I avoided using parameters or literal constants as internal files.

    To be portable, you need to do the assignment, or you need to declare
    goes(*) as a variable rather than a parameter. I never understood why
    the limitation was in the standard. In my codes, I usually left a
    comment explaining why the code was written that way so that I would not
    change it a month later by mistake. That comment was, of course, a
    separate line beginning with C or *, it was not on the same line. F77
    was so limited in so many ways.

    $.02 -Ron Shepard

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From gah4@21:1/5 to Ron Shepard on Mon Jun 20 16:24:28 2022
    On Sunday, June 19, 2022 at 7:48:57 AM UTC-7, Ron Shepard wrote:

    (snip)

    It is a standard restriction in f77. I remember similar situations many
    times in the 1980s.

    There were some strange restrictions in Fortran 66, some of which
    were removed in Fortran 77.

    The I/O list of READ and WRITE statements contains variables (and arrays)
    but not constants or expressions. That is obvious for READ, but not
    for WRITE.

    I believe at the time, actually using WATFIV before 1977, that expressions
    in the I/O list of WRITE statements was my favorite new feature.

    In Fortran 66, the format part of a READ/WRITE statement is either a
    statement number (of a FORMAT statement) or an array with a run-time
    format, character data read in A format, or initialized in DATA statements.

    Even if it fit i a scalar, it was required to be an array.

    Fortran 77 added internal I/O, putting a character variable in place
    of the unit number. There are some not so obvious restrictions on it,
    but similar to above, can't be a constant.

    And now, so many years later, we wonder why.

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Phillip Helbig (undress to reply@21:1/5 to gah4@u.washington.edu on Tue Jun 21 10:38:46 2022
    In article <66596868-5be6-48c3-8120-73977567ac22n@googlegroups.com>,
    gah4 <gah4@u.washington.edu> writes:

    The I/O list of READ and WRITE statements contains variables (and arrays)
    but not constants or expressions. That is obvious for READ, but not
    for WRITE.

    Vice versa?

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)