Patchwork [gimplefe] Patch for recognizing function declarations

login
register
mail settings
Submitter Sandeep Soni
Date July 31, 2012, 6:06 p.m.
Message ID <CANY-sXUQQN-mhTkvJ_nwnnE+D2CbOHihKVMd_EZDYReS4cMQbQ@mail.gmail.com>
Download mbox | patch
Permalink /patch/174299/
State New
Headers show

Comments

Sandeep Soni - July 31, 2012, 6:06 p.m.
Hi Diego,

The following patch recognizes function declarations. I am now trying
to create a gimple sequence of all the statements within the function
body.
The chagelog is as follows:

2012-07-31   Sandeep Soni <soni.sandeepb@gmail.com>

	* parser.c (gl_token_starts_decl): Modify. Matches function decls.
	(gp_parse_parm_decl): New.
	(gp_parse_return_type): New.
	(gp_parse_function_decl): New.
	(gp_parse_decl): Modify. Adds case for function decls.
Dodji Seketeli - Aug. 1, 2012, 9:31 a.m.
Hello,

Sandeep Soni <soni.sandeepb@gmail.com> a écrit:

> Hi Diego,
>
> The following patch recognizes function declarations. I am now trying
> to create a gimple sequence of all the statements within the function
> body.
> The chagelog is as follows:
>
> 2012-07-31   Sandeep Soni <soni.sandeepb@gmail.com>
>
> 	* parser.c (gl_token_starts_decl): Modify. Matches function decls.
> 	(gp_parse_parm_decl): New.
> 	(gp_parse_return_type): New.
> 	(gp_parse_function_decl): New.
> 	(gp_parse_decl): Modify. Adds case for function decls.

Just a random note.

For casual patch readers like myself, it would be nice to have test
cases added to commits like this, so that we have a better idea of the
syntax we are parsing against.

The functions are greatly commented in the patch, which helps, but I
think having test cases would be even better.

Thanks.
Diego Novillo - Aug. 2, 2012, 5:06 p.m.
On Tue, Jul 31, 2012 at 11:06 AM, Sandeep Soni <soni.sandeepb@gmail.com> wrote:

> +/* The syntax of a function declaration is as follows:
> +
> +   FUNCTION_DECL<Name, Type, Parms>
> +   <
> +      function body
> +   >
> +
> +   Here, each of the PARMS in itself is a parameter declaration similar to a
> +   variable declaration, TYPE is the type of the variable that this
> +   function returns and FUNCTION BODY is the series of statements that define
> +   the beahavior of the function.
> +
> +   Following are some of the examples for which the syntax of the function
> +   declarations are described.
> +
> +   1. C-like function as
> +      void foo (int first, float second)
> +        {
> +          first = second;
> +        }
> +
> +   The corresponding gimple syntax is:
> +     FUNCTION_DECL <foo, VOID_TYPE,
> +                    PARM_DECL<first, INTEGER_TYPE<4>>,
> +                    PARM_DECL<second, REAL_TYPE<4>>>
> +     <
> +       GIMPLE_ASSIGN <PARM_DECL,first, second, NULL>
> +     >
> +
> +   2. C-like function as
> +      int foo (int first, float second)
> +       {
> +          int local_first;
> +          float local_second;
> +
> +          local_first = first;
> +          local_second = second;
> +
> +          return local_first;
> +       }
> +
> +   The corresponding gimple syntax is:
> +     FUNCTION_DECL <foo, INTEGER_TYPE<4>,
> +                    PARM_DECL<first, INTEGER_TYPE<4>>,
> +                    PARM_DECL<second, REAL_TYPE<4>>>
> +     <
> +        VAR_DECL <local_first, INTEGER_TYPE<4>>
> +       VAR_DECL <local_second, REAL_TYPE<4>>
> +       VAR_DECL <return_var, INTEGER_TYPE<4>>
> +
> +       gimple_assign <parm_decl, local_first, first, NULL>
> +       gimple_assign <parm_decl, local_second, second, NULL>
> +       gimple_assign <parm_decl, return_var, first, NULL>
> +       gimple_return <return_var>
> +     >
> +
> +   Note: 1) The syntax closely mimics the -fdump-tree-gimple-raw option.
> +        2) The function declaration tuple needs to be checked against the
> +           call of the function for order and the number of arguments.
> +        3) A symbol table entry for the function should be made. The
> +           variables defined within the function should be made to have
> +           function scope.  */

Nice.  Thanks for this documentation.

> +  next_token = gl_consume_token (parser->lexer);
> +  while (!gl_at_eof(parser->lexer))

Space before '('.

> +    {
> +      if (next_token->type == CPP_COMMA)
> +       {
> +         next_token = gl_consume_token (parser->lexer);
> +         if (gl_tree_code_for_token (next_token) == PARM_DECL)
> +            gp_parse_parm_decl (parser);
> +         else
> +           error_at (next_token->location,
> +                     "Unsupported declaration of parameters");
> +      else if (next_token->type == CPP_GREATER)
> +       break;
> +    }

Could you factor this into its own function? You will likely need to
parse other comma-separated lists.

Also, please add some test cases with the patch.


Diego.

Patch

Index: gcc/gimple/parser.c
===================================================================
--- gcc/gimple/parser.c	(revision 188546)
+++ gcc/gimple/parser.c	(working copy)
@@ -234,7 +271,7 @@ 
 gl_token_starts_decl (gimple_token *token)
 {
   enum tree_code code = gl_tree_code_for_token (token);
-  return code == VAR_DECL;
+  return code == VAR_DECL || code == FUNCTION_DECL;
 }


@@ -746,6 +817,24 @@ 
 }


+/* Helper for gp_parse_function_decl. The parm_decl's
+   are read from gimple_parser PARSER.  */
+
+static void
+gp_parse_parm_decl (gimple_parser *parser)
+{
+  gl_consume_expected_token (parser->lexer, CPP_LESS);
+  gl_consume_expected_token (parser->lexer, CPP_NAME);
+  gl_consume_expected_token (parser->lexer, CPP_COMMA);
+  gl_consume_expected_token (parser->lexer, CPP_NAME);
+  gl_consume_expected_token (parser->lexer, CPP_LESS);
+  gl_consume_expected_token (parser->lexer, CPP_NUMBER);
+  gl_consume_expected_token (parser->lexer, CPP_GREATER);
+  gl_consume_expected_token (parser->lexer, CPP_GREATER);
+
+}
+
+
 /* Helper for gp_parse_expect_record_type and
    gp_parse_expect_union_type. The field_decl's
    are read from gimple_parser PARSER.  */
@@ -939,6 +1028,27 @@ 
 }


+/* Recognizes the return type of the function. The tuple is read from
+   PARSER.  */
+
+static void
+gp_parse_return_type (gimple_parser *parser)
+{
+  gimple_token *next_token = gl_consume_token (parser->lexer);
+  enum tree_code code = gl_tree_code_for_token (next_token);
+
+  switch (code)
+  {
+  case INTEGER_TYPE:
+  case REAL_TYPE:
+    gl_consume_expected_token (parser->lexer, CPP_LESS);
+    gl_consume_expected_token (parser->lexer, CPP_NUMBER);
+    gl_consume_expected_token (parser->lexer, CPP_GREATER);
+    break;
+  }
+}
+
+
 /* The Declaration section within a .gimple file can consist of
    a) Declaration of variables.
    b) Declaration of functions.
@@ -1070,6 +1180,103 @@ 
 }


+/* The syntax of a function declaration is as follows:
+
+   FUNCTION_DECL<Name, Type, Parms>
+   <
+      function body
+   >
+
+   Here, each of the PARMS in itself is a parameter declaration similar to a
+   variable declaration, TYPE is the type of the variable that this
+   function returns and FUNCTION BODY is the series of statements that define
+   the beahavior of the function.
+
+   Following are some of the examples for which the syntax of the function
+   declarations are described.
+
+   1. C-like function as
+      void foo (int first, float second)
+        {
+	   first = second;
+        }
+
+   The corresponding gimple syntax is:
+     FUNCTION_DECL <foo, VOID_TYPE,
+                    PARM_DECL<first, INTEGER_TYPE<4>>,
+                    PARM_DECL<second, REAL_TYPE<4>>>
+     <
+	GIMPLE_ASSIGN <PARM_DECL,first, second, NULL>
+     >
+
+   2. C-like function as
+      int foo (int first, float second)
+	{
+	   int local_first;
+	   float local_second;
+	
+	   local_first = first;
+	   local_second = second;
+
+	   return local_first;
+	}
+
+   The corresponding gimple syntax is:
+     FUNCTION_DECL <foo, INTEGER_TYPE<4>,
+                    PARM_DECL<first, INTEGER_TYPE<4>>,
+                    PARM_DECL<second, REAL_TYPE<4>>>
+     <
+        VAR_DECL <local_first, INTEGER_TYPE<4>>
+	VAR_DECL <local_second, REAL_TYPE<4>>
+	VAR_DECL <return_var, INTEGER_TYPE<4>>
+
+  	gimple_assign <parm_decl, local_first, first, NULL>
+  	gimple_assign <parm_decl, local_second, second, NULL>
+  	gimple_assign <parm_decl, return_var, first, NULL>
+  	gimple_return <return_var>
+     >
+
+   Note: 1) The syntax closely mimics the -fdump-tree-gimple-raw option.
+	 2) The function declaration tuple needs to be checked against the
+	    call of the function for order and the number of arguments.
+	 3) A symbol table entry for the function should be made. The
+	    variables defined within the function should be made to have
+	    function scope.  */
+
+/* Recognizer function for function declarations. The declaration tuple is read
+   from gimple_parser PARSER.  */
+
+static void
+gp_parse_function_decl (gimple_parser *parser)
+{
+  const gimple_token *next_token;
+
+  gl_consume_expected_token (parser->lexer, CPP_LESS);
+  gl_consume_expected_token (parser->lexer, CPP_NAME);
+  gl_consume_expected_token (parser->lexer, CPP_COMMA);
+  gp_parse_return_type (parser);
+
+  next_token = gl_consume_token (parser->lexer);
+  while (!gl_at_eof(parser->lexer))
+    {
+      if (next_token->type == CPP_COMMA)
+	{
+	  next_token = gl_consume_token (parser->lexer);
+	  if (gl_tree_code_for_token (next_token) == PARM_DECL)
+            gp_parse_parm_decl (parser);
+	  else
+	    error_at (next_token->location,
+		      "Unsupported declaration of parameters");
+      else if (next_token->type == CPP_GREATER)
+	break;
+    }
+
+  /* TODO The function signature should be changed to parse a gimple
+     function and the call to parse the function body should be made
+     here.  */
+}
+
+
 /* The token TOKEN read from the reader PARSER is looked up for a match.
    Calls the corresponding function to do the parsing for the match.
    Gets called for recognizing variable and function declarations. */
@@ -1084,6 +1291,10 @@ 
       gp_parse_var_decl (parser);
       break;

+    case FUNCTION_DECL:
+      gp_parse_function_decl (parser);
+      break;
+
     default:
       break;
     }
@@ -1211,6 +1422,7 @@ 
   return itk_none;
 }

+
 /* Returns true if the type of the TOKEN is equal to EXPECTED.  */

 static bool
@@ -1219,6 +1431,7 @@ 
   return (token->type == expected);
 }

+
 /* Splits the token TOKEN into two tokens FIRST_TOKEN and SECOND_TOKEN.
    Note that the split should work only if the type of the TOKEN is
    either CPP_RSHIFT or CPP_LSHIFT which gets split into two tokens
@@ -1249,6 +1462,7 @@ 
   first_token->value = second_token->value = token->value;
 }

+
 /* Interpret TOKEN, an integer with FLAGS as classified by cpplib.  */

 static tree