https://gcc.gnu.org/g:17582084fad3a0fbf72a83524a4100d2eb802107
commit r16-6748-g17582084fad3a0fbf72a83524a4100d2eb802107 Author: Jerry DeLisle <[email protected]> Date: Mon Jan 12 18:45:05 2026 -0800 Fortran: Detect missing quote in namelist read. PR libfortran/123012 libgfortran/ChangeLog: * io/list_read.c (read_character): Add new check after get_string and provide better comments. gcc/testsuite/ChangeLog: * gfortran.dg/namelist_101.f90: New test. Diff: --- gcc/testsuite/gfortran.dg/namelist_101.f90 | 16 ++++++++++++++++ libgfortran/io/list_read.c | 14 ++++++++++++++ 2 files changed, 30 insertions(+) diff --git a/gcc/testsuite/gfortran.dg/namelist_101.f90 b/gcc/testsuite/gfortran.dg/namelist_101.f90 new file mode 100644 index 000000000000..409c568f53f3 --- /dev/null +++ b/gcc/testsuite/gfortran.dg/namelist_101.f90 @@ -0,0 +1,16 @@ +! { dg-do run ) +! { dg-shouldfail "Missing quote" } +program nml_quotes_bug + implicit none + integer :: unit = 10 + character(8) :: c1, c2 + namelist /tovs_obs_chan/ c1, c2 + open (unit ,file="nml-quotes-bug.nml") + write(unit,*) "&tovs_obs_chan" + write(unit,*) " c1 = '1'," + write(unit,*) " c2 = 2a ," + write(unit,*) "/" + rewind(unit) + read (unit ,nml=tovs_obs_chan) + close(unit ,status="delete") +end program nml_quotes_bug diff --git a/libgfortran/io/list_read.c b/libgfortran/io/list_read.c index 2aadc8f4d3c1..0d16640a9000 100644 --- a/libgfortran/io/list_read.c +++ b/libgfortran/io/list_read.c @@ -1314,6 +1314,10 @@ read_character (st_parameter_dt *dtp, int length __attribute__ ((unused))) CASE_SEPARATORS: case EOF: + /* At this point we have been reading a string of digits. Now we see + the end of these digits without seeing the closing quote and not + seeing the '*' for a repeat count. When in namelist mode, if it + was a string of digits it should have had the closing quote. */ if (dtp->u.p.namelist_mode) { snprintf (message, IOMSG_LEN, "Missing quote while reading item %d", @@ -1367,6 +1371,16 @@ read_character (st_parameter_dt *dtp, int length __attribute__ ((unused))) get_string: + /* We could be at the beginning of a string or partially through a string + that began with all digits. Either way, the quote character for a namelist + read should have been set. */ + if (dtp->u.p.namelist_mode && (quote == ' ')) + { + snprintf (message, IOMSG_LEN, "Missing quote while reading item %d", + dtp->u.p.item_count); + generate_error (&dtp->common, LIBERROR_READ_VALUE, message); + } + for (;;) { if ((c = next_char (dtp)) == EOF)
