[05/55] rs6000: Add helper functions for parsing

Message ID 643ab7459789d98707031c6081e686608030c864.1623941441.git.wschmidt@linux.ibm.com
State New
Headers show
Series
  • Replace the Power target-specific builtin machinery
Related show

Commit Message

Jeff Law via Gcc-patches June 17, 2021, 3:18 p.m.
2021-06-07  Bill Schmidt  <wschmidt@linux.ibm.com>

gcc/
	* config/rs6000/rs6000-gen-builtins.c (consume_whitespace): New
	function.
	(advance_line): Likewise.
	(safe_inc_pos): Likewise.
	(match_identifier): Likewise.
	(match_integer): Likewise.
	(match_to_right_bracket): Likewise.
---
 gcc/config/rs6000/rs6000-gen-builtins.c | 111 ++++++++++++++++++++++++
 1 file changed, 111 insertions(+)

-- 
2.27.0

Comments

Jeff Law via Gcc-patches July 9, 2021, 7:32 p.m. | #1
On Thu, 2021-06-17 at 10:18 -0500, Bill Schmidt via Gcc-patches wrote:
> 2021-06-07  Bill Schmidt  <wschmidt@linux.ibm.com>

> 

> gcc/

> 	* config/rs6000/rs6000-gen-builtins.c (consume_whitespace): New

> 	function.

> 	(advance_line): Likewise.

> 	(safe_inc_pos): Likewise.

> 	(match_identifier): Likewise.

> 	(match_integer): Likewise.

> 	(match_to_right_bracket): Likewise.

> ---

>  gcc/config/rs6000/rs6000-gen-builtins.c | 111 ++++++++++++++++++++++++

>  1 file changed, 111 insertions(+)

> 

> diff --git a/gcc/config/rs6000/rs6000-gen-builtins.c b/gcc/config/rs6000/rs6000-gen-builtins.c

> index 3c53c3401b2..c5d5590e865 100644

> --- a/gcc/config/rs6000/rs6000-gen-builtins.c

> +++ b/gcc/config/rs6000/rs6000-gen-builtins.c

> @@ -210,3 +210,114 @@ ovld_diag (const char * fmt, ...)

>    vfprintf (stderr, fmt, args);

>    va_end (args);

>  }

> +

> +/* Pass over unprintable characters and whitespace (other than a newline,

> +   which terminates the scan).  */


AFAIK isspace() and thusly this helper only skips whitespace, so
nothing unprintable is actually handled or skipped here.
Beyond that comment nit the function seems OK.

> +static void

> +consume_whitespace (void)

> +{

> +  while (pos < LINELEN && isspace(linebuf[pos]) && linebuf[pos] != '\n')

> +    pos++;

> +  return;

> +}

> +

> +/* Get the next nonblank, noncomment line, returning 0 on EOF, 1 otherwise.  */

> +static int

> +advance_line (FILE *file)

> +{

> +  while (1)

> +    {

> +      /* Read ahead one line and check for EOF.  */

> +      if (!fgets (linebuf, sizeof linebuf, file))

> +	return 0;

> +      line++;

> +      size_t len = strlen (linebuf);

> +      if (linebuf[len - 1] != '\n')

> +	(*diag) ("line doesn't terminate with newline\n");

> +      pos = 0;

> +      consume_whitespace ();

> +      if (linebuf[pos] != '\n' && linebuf[pos] != ';')

> +	return 1;

> +    }

> +}

ok

> +

> +static inline void

> +safe_inc_pos (void)

> +{

> +  if (pos++ >= LINELEN)

> +    {

> +      (*diag) ("line length overrun.\n");

> +      exit (1);

> +    }

> +}


ok

> +

> +/* Match an identifier, returning NULL on failure, else a pointer to a

> +   buffer containing the identifier.  */

> +static char *

> +match_identifier (void)

> +{

> +  int lastpos = pos - 1;

> +  while (isalnum (linebuf[lastpos + 1]) || linebuf[lastpos + 1] == '_')

> +    ++lastpos;

> +

> +  if (lastpos < pos)

> +    return 0;

> +

> +  char *buf = (char *) malloc (lastpos - pos + 2);

> +  memcpy (buf, &linebuf[pos], lastpos - pos + 1);

> +  buf[lastpos - pos + 1] = '\0';

> +

> +  pos = lastpos + 1;

> +  return buf;

> +}

ok


> +

> +/* Match an integer and return the string representing its value,

> +   or a null string on failure.  */

> +static char *

> +match_integer (void)

> +{

> +  int startpos = pos;

> +  if (linebuf[pos] == '-')

> +    safe_inc_pos ();

> +

> +  int lastpos = pos - 1;

> +  while (isdigit (linebuf[lastpos + 1]))

> +    ++lastpos;

> +

> +  if (lastpos < pos)

> +    return NULL;

> +

> +  pos = lastpos + 1;

> +  char *buf = (char *) malloc (lastpos - startpos + 2);

> +  memcpy (buf, &linebuf[startpos], lastpos - startpos + 1);

> +  buf[lastpos - startpos + 1] = '\0';

> +  return buf;

> +}

Ok

> +

> +/* Match a string up to but not including a ']', and return its value,

> +   or zero if there is nothing before the ']'.  Error if we don't find

> +   such a character.  */

> +static const char *

> +match_to_right_bracket (void)

> +{

> +  int lastpos = pos - 1;

> +  while (linebuf[lastpos + 1] != ']')

> +    {

> +      if (linebuf[lastpos + 1] == '\n')

> +	{

> +	  (*diag) ("no ']' found before end of line.\n");

> +	  exit (1);

> +	}

> +      ++lastpos;

> +    }

> +

> +  if (lastpos < pos)

> +    return 0;

> +

> +  char *buf = (char *) malloc (lastpos - pos + 2);

> +  memcpy (buf, &linebuf[pos], lastpos - pos + 1);

> +  buf[lastpos - pos + 1] = '\0';

> +

> +  pos = lastpos + 1;

> +  return buf;

> +}


Ok. 

presumably all tested OK.. :-)

lgtm, 
thanks
-Will
Segher Boessenkool July 14, 2021, 10:58 p.m. | #2
Hi!

On Fri, Jul 09, 2021 at 02:32:59PM -0500, will schmidt wrote:
> On Thu, 2021-06-17 at 10:18 -0500, Bill Schmidt via Gcc-patches wrote:

> > 2021-06-07  Bill Schmidt  <wschmidt@linux.ibm.com>

> > +/* Pass over unprintable characters and whitespace (other than a newline,

> > +   which terminates the scan).  */


> > +static void

> > +consume_whitespace (void)

> > +{

> > +  while (pos < LINELEN && isspace(linebuf[pos]) && linebuf[pos] != '\n')

> > +    pos++;

> > +  return;

> > +}


> AFAIK isspace() and thusly this helper only skips whitespace, so

> nothing unprintable is actually handled or skipped here.


Right, and that behaviour would not match with the function name either.
isspace returns true for 0x09..0x0d and 0x20, all of which are
whitespace.


Segher
Segher Boessenkool July 14, 2021, 11:32 p.m. | #3
Hi!

On Thu, Jun 17, 2021 at 10:18:49AM -0500, Bill Schmidt wrote:
> 	* config/rs6000/rs6000-gen-builtins.c (consume_whitespace): New

> 	function.

> 	(advance_line): Likewise.

> 	(safe_inc_pos): Likewise.

> 	(match_identifier): Likewise.

> 	(match_integer): Likewise.

> 	(match_to_right_bracket): Likewise.


> +/* Pass over unprintable characters and whitespace (other than a newline,

> +   which terminates the scan).  */


See Will's review :-)

> +  buf[lastpos - startpos + 1] = '\0';


Just "= 0"?  It means exactly the same.

You can write just
  diag ("bla bla bla")
instead of
  (*diag) ("bla bla bla");
btw.

The patch is okay for trunk with whatever you want to do with those
comments (but do fix the consume_whitespace comment please).  Thanks!


Segher

Patch

diff --git a/gcc/config/rs6000/rs6000-gen-builtins.c b/gcc/config/rs6000/rs6000-gen-builtins.c
index 3c53c3401b2..c5d5590e865 100644
--- a/gcc/config/rs6000/rs6000-gen-builtins.c
+++ b/gcc/config/rs6000/rs6000-gen-builtins.c
@@ -210,3 +210,114 @@  ovld_diag (const char * fmt, ...)
   vfprintf (stderr, fmt, args);
   va_end (args);
 }
+
+/* Pass over unprintable characters and whitespace (other than a newline,
+   which terminates the scan).  */
+static void
+consume_whitespace (void)
+{
+  while (pos < LINELEN && isspace(linebuf[pos]) && linebuf[pos] != '\n')
+    pos++;
+  return;
+}
+
+/* Get the next nonblank, noncomment line, returning 0 on EOF, 1 otherwise.  */
+static int
+advance_line (FILE *file)
+{
+  while (1)
+    {
+      /* Read ahead one line and check for EOF.  */
+      if (!fgets (linebuf, sizeof linebuf, file))
+	return 0;
+      line++;
+      size_t len = strlen (linebuf);
+      if (linebuf[len - 1] != '\n')
+	(*diag) ("line doesn't terminate with newline\n");
+      pos = 0;
+      consume_whitespace ();
+      if (linebuf[pos] != '\n' && linebuf[pos] != ';')
+	return 1;
+    }
+}
+
+static inline void
+safe_inc_pos (void)
+{
+  if (pos++ >= LINELEN)
+    {
+      (*diag) ("line length overrun.\n");
+      exit (1);
+    }
+}
+
+/* Match an identifier, returning NULL on failure, else a pointer to a
+   buffer containing the identifier.  */
+static char *
+match_identifier (void)
+{
+  int lastpos = pos - 1;
+  while (isalnum (linebuf[lastpos + 1]) || linebuf[lastpos + 1] == '_')
+    ++lastpos;
+
+  if (lastpos < pos)
+    return 0;
+
+  char *buf = (char *) malloc (lastpos - pos + 2);
+  memcpy (buf, &linebuf[pos], lastpos - pos + 1);
+  buf[lastpos - pos + 1] = '\0';
+
+  pos = lastpos + 1;
+  return buf;
+}
+
+/* Match an integer and return the string representing its value,
+   or a null string on failure.  */
+static char *
+match_integer (void)
+{
+  int startpos = pos;
+  if (linebuf[pos] == '-')
+    safe_inc_pos ();
+
+  int lastpos = pos - 1;
+  while (isdigit (linebuf[lastpos + 1]))
+    ++lastpos;
+
+  if (lastpos < pos)
+    return NULL;
+
+  pos = lastpos + 1;
+  char *buf = (char *) malloc (lastpos - startpos + 2);
+  memcpy (buf, &linebuf[startpos], lastpos - startpos + 1);
+  buf[lastpos - startpos + 1] = '\0';
+  return buf;
+}
+
+/* Match a string up to but not including a ']', and return its value,
+   or zero if there is nothing before the ']'.  Error if we don't find
+   such a character.  */
+static const char *
+match_to_right_bracket (void)
+{
+  int lastpos = pos - 1;
+  while (linebuf[lastpos + 1] != ']')
+    {
+      if (linebuf[lastpos + 1] == '\n')
+	{
+	  (*diag) ("no ']' found before end of line.\n");
+	  exit (1);
+	}
+      ++lastpos;
+    }
+
+  if (lastpos < pos)
+    return 0;
+
+  char *buf = (char *) malloc (lastpos - pos + 2);
+  memcpy (buf, &linebuf[pos], lastpos - pos + 1);
+  buf[lastpos - pos + 1] = '\0';
+
+  pos = lastpos + 1;
+  return buf;
+}