From a240e83ce9d92786ac9a15ab815b58197b85ada2 Mon Sep 17 00:00:00 2001 From: =?utf8?q?Jos=C3=A9=20Rui=20Faustino=20de=20Sousa?= Date: Sun, 30 Aug 2020 18:10:15 +0000 Subject: [PATCH] =?utf8?q?=092020-8-20=20=20Jos=C3=A9=20Rui=20Faustino=20d?= =?utf8?q?e=20Sousa=20=20?= MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit gcc/fortran/ChangeLog: PR fortran/96728 * module.c (module_peek_char): Peek ahead function. (parse_integer): Add code for parsing signed integers. (parse_atom): Add code to handle signed integers. (peek_atom): Add code to handle signed integers. gcc/testsuite/ChangeLog: PR fortran/96728 * gfortran.dg/PR96728.f90: New test. --- gcc/fortran/module.c | 42 ++++++++++++++++++++++- gcc/testsuite/gfortran.dg/PR96728.f90 | 49 +++++++++++++++++++++++++++ 2 files changed, 90 insertions(+), 1 deletion(-) create mode 100644 gcc/testsuite/gfortran.dg/PR96728.f90 diff --git a/gcc/fortran/module.c b/gcc/fortran/module.c index 714fbd9c299..33e7df7d6a4 100644 --- a/gcc/fortran/module.c +++ b/gcc/fortran/module.c @@ -1234,6 +1234,13 @@ get_module_locus (module_locus *m) m->pos = module_pos; } +/* Peek at the next character in the module. */ + +static int +module_peek_char (void) +{ + return module_content[module_pos]; +} /* Get the next character in the module, updating our reckoning of where we are. */ @@ -1314,7 +1321,19 @@ parse_string (void) static void parse_integer (int c) { - atom_int = c - '0'; + int sign = 1; + + atom_int = 0; + switch (c) + { + case ('-'): + sign = -1; + case ('+'): + break; + default: + atom_int = c - '0'; + break; + } for (;;) { @@ -1328,6 +1347,7 @@ parse_integer (int c) atom_int = 10 * atom_int + c - '0'; } + atom_int *= sign; } @@ -1401,6 +1421,16 @@ parse_atom (void) parse_integer (c); return ATOM_INTEGER; + case '+': + case '-': + if (ISDIGIT (module_peek_char ())) + { + parse_integer (c); + return ATOM_INTEGER; + } + else + bad_module ("Bad name"); + case 'a': case 'b': case 'c': @@ -1504,6 +1534,16 @@ peek_atom (void) module_unget_char (); return ATOM_INTEGER; + case '+': + case '-': + if (ISDIGIT (module_peek_char ())) + { + module_unget_char (); + return ATOM_INTEGER; + } + else + bad_module ("Bad name"); + case 'a': case 'b': case 'c': diff --git a/gcc/testsuite/gfortran.dg/PR96728.f90 b/gcc/testsuite/gfortran.dg/PR96728.f90 new file mode 100644 index 00000000000..4caa3a569a7 --- /dev/null +++ b/gcc/testsuite/gfortran.dg/PR96728.f90 @@ -0,0 +1,49 @@ +! { dg-do run } +! +! Test the fix for PR96728 +! + +module cref_m + + implicit none + + private + + public :: & + isub_a_m + +contains + + subroutine isub_a_m(a, b) + integer, intent(in) :: a(..) + integer, intent(out) :: b(size(a)) + + integer :: i + + b = [(i, i=1,size(b))] + return + end subroutine isub_a_m + +end module cref_m + +program cref_p + + use cref_m, only: & + isub_a_m + + implicit none + + integer :: i + + integer, parameter :: n = 3 + integer, parameter :: p(*) = [(i, i=1,n*n)] + + integer :: a(n,n) + integer :: b(n*n) + + a = reshape(p, shape=[n,n]) + call isub_a_m(a, b) + if (any(b/=p)) stop 1 + stop + +end program cref_p -- 2.30.2