bug-make
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[PATCH v2 4/6] * read.c: Construct the dependency chain between parent a


From: Macpaul Lin
Subject: [PATCH v2 4/6] * read.c: Construct the dependency chain between parent and target variable
Date: Mon, 18 Aug 2014 21:27:13 +0800

(eval_makefile): deal with new parent_records paremeter for API consistancy,
(eval): assign related parent_records to target variable, and construct
tempoaray parent_records when ifdef/ifeq conditional_line is parsed.
(conditional_line): when ifdef/ifeq conditional_line is encountered,
construct tempoaray parent_records for later dependency chain assignment for
the target variable.

Signed-off-by: Macpaul Lin <address@hidden>
---
Changes for v2:
  - (eval): fix the problem of mapping the same parent_records set to multiple
    variable in the same ifdef/ifeq depth.
  - (conditional_line): add if_cmds->depth support.

 read.c | 109 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++------
 1 file changed, 99 insertions(+), 10 deletions(-)

diff --git a/read.c b/read.c
index 6ac66f4..4311195 100644
--- a/read.c
+++ b/read.c
@@ -142,7 +142,11 @@ static void do_undefine (char *name, enum variable_origin 
origin,
                          struct ebuffer *ebuf);
 static struct variable *do_define (char *name, enum variable_origin origin,
                                    struct ebuffer *ebuf);
-static int conditional_line (char *line, int len, const gmk_floc *flocp);
+struct parent_record *dup_parent_records (struct parent_record **dst_pr,
+                                          struct parent_record *src_pr);
+void free_parent_record (struct parent_record *pr);
+static int conditional_line (char *line, int len, const gmk_floc *flocp,
+                             struct parent_record **parents);
 static void record_files (struct nameseq *filenames, const char *pattern,
                           const char *pattern_percent, char *depstr,
                           unsigned int cmds_started, char *commands,
@@ -432,7 +436,7 @@ eval_makefile (const char *filename, int flags)
 
   /* Add this makefile to the list. */
   do_variable_definition (&ebuf.floc, "MAKEFILE_LIST", filename, o_file,
-                          f_append, 0);
+                          f_append, 0, NULL);
 
   /* Evaluate the makefile */
 
@@ -591,6 +595,8 @@ eval (struct ebuffer *ebuf, int set_default)
   const char *pattern_percent;
   gmk_floc *fstart;
   gmk_floc fi;
+  struct parent_record *parents = NULL;
+  struct parent_record *new_parents = NULL;
 
 #define record_waiting_files()                                                \
   do                                                                          \
@@ -749,7 +755,14 @@ eval (struct ebuffer *ebuf, int set_default)
           else if (vmod.define_v)
             v = do_define (p, origin, ebuf);
           else
-            v = try_variable_definition (fstart, p, origin, 0);
+            {
+              /* duplicate parent_records to avoid wrong link caused by sharing
+                 the same parent_records between variables in the same ifeq
+                 depth  */
+              dup_parent_records(&new_parents, parents);
+
+              v = try_variable_definition (fstart, p, origin, 0, new_parents);
+            }
 
           assert (v != NULL);
 
@@ -782,7 +795,7 @@ eval (struct ebuffer *ebuf, int set_default)
 
       /* Check for conditional state changes.  */
       {
-        int i = conditional_line (p, wlen, fstart);
+        int i = conditional_line (p, wlen, fstart, &parents);
         if (i != -2)
           {
             if (i == -1)
@@ -1549,7 +1562,7 @@ do_define (char *name, enum variable_origin origin, 
struct ebuffer *ebuf)
     definition[idx - 1] = '\0';
 
   v = do_variable_definition (&defstart, name,
-                              definition, origin, var.flavor, 0);
+                              definition, origin, var.flavor, 0, NULL);
   free (definition);
   free (n);
   return (v);
@@ -1568,12 +1581,14 @@ do_define (char *name, enum variable_origin origin, 
struct ebuffer *ebuf)
    1 if following text should be ignored.  */
 
 static int
-conditional_line (char *line, int len, const gmk_floc *flocp)
+conditional_line (char *line, int len, const gmk_floc *flocp, struct 
parent_record **parents)
 {
   const char *cmdname;
   enum { c_ifdef, c_ifndef, c_ifeq, c_ifneq, c_else, c_endif } cmdtype;
   unsigned int i;
   unsigned int o;
+  struct variable *current_parent = NULL;
+  struct parent_record *temp_pr;
 
   /* Compare a word, both length and contents. */
 #define word1eq(s)      (len == CSTRLEN (s) && strneq (s, line, CSTRLEN (s)))
@@ -1604,6 +1619,33 @@ conditional_line (char *line, int len, const gmk_floc 
*flocp)
       if (!conditionals->if_cmds)
         EXTRACMD ();
 
+      /* Remove temp parent_records belongs to this depth  */
+      temp_pr = (*parents);
+      if (temp_pr != NULL)
+        {
+          /* Root depth */
+          if (temp_pr->depth == conditionals->if_cmds)
+            {
+              free_parent_record (temp_pr);
+              *parents = NULL;
+            }
+          else
+            {
+              while (temp_pr->next != NULL)
+                {
+                  /* The next parent_record is not the start node of this 
depth */
+                  if (temp_pr->next->depth < conditionals->if_cmds)
+                    temp_pr = temp_pr->next;
+                  else
+                    {
+                      free_parent_record (temp_pr->next);
+                      temp_pr->next = NULL;
+                      break;
+                    }
+                }
+            }
+        }
+
       --conditionals->if_cmds;
 
       goto DONE;
@@ -1653,7 +1695,7 @@ conditional_line (char *line, int len, const gmk_floc 
*flocp)
 
       /* If it's 'else' or 'endif' or an illegal conditional, fail.  */
       if (word1eq ("else") || word1eq ("endif")
-          || conditional_line (line, len, flocp) < 0)
+          || conditional_line (line, len, flocp, parents) < 0)
         EXTRATEXT ();
       else
         {
@@ -1721,12 +1763,32 @@ conditional_line (char *line, int len, const gmk_floc 
*flocp)
       conditionals->ignoring[o] =
         ((v != 0 && *v->value != '\0') == (cmdtype == c_ifndef));
 
+      /* deal with defined parent of variables  */
+      current_parent = v;
+      /* if v is defined  */
+      if ((current_parent != NULL) && (parents != NULL))
+        {
+          /* the first parent */
+          if (*parents == NULL)
+            *parents = alloc_parent_record (current_parent, 
conditionals->if_cmds);
+          else
+            {
+              /* check the last parent updated  */
+              temp_pr = (*parents);
+              while (temp_pr->next != NULL)
+                temp_pr = temp_pr->next;
+
+              if (current_parent != temp_pr->parent)
+                temp_pr->next = alloc_parent_record (current_parent, 
conditionals->if_cmds);
+            }
+        }
+
       free (var);
     }
   else
     {
       /* "ifeq" or "ifneq".  */
-      char *s1, *s2;
+      char *s1, *s2, *ps;
       unsigned int l;
       char termin = *line == '(' ? ',' : *line;
 
@@ -1764,6 +1826,33 @@ conditional_line (char *line, int len, const gmk_floc 
*flocp)
       else
         *line++ = '\0';
 
+      /* Check if this variable is defined before.  */
+      /* s1: source string, s2: pointer to variable name,
+         s3: pointer to closeparen */
+      s2 = variable_name_extract(s1, &ps);
+      if ((s2 != NULL) && (ps != NULL))
+        current_parent = lookup_variable (s2, ps - s2);
+
+      /* If this variable is defined, prepare a temp parent_records
+         for later variable definition. */
+      if ((current_parent != NULL) && (parents != NULL))
+        {
+          /* The first parent. */
+          if (*parents == NULL)
+            *parents = alloc_parent_record (current_parent, 
conditionals->if_cmds);
+          else
+            {
+              /* Check the if the last parent_record is changed.
+                 This means a new parent variable is checked */
+              temp_pr = (*parents);
+              while (temp_pr->next != NULL)
+                  temp_pr = temp_pr->next;
+
+              if (current_parent != temp_pr->parent)
+                temp_pr->next = alloc_parent_record (current_parent, 
conditionals->if_cmds);
+            }
+        }
+
       s2 = variable_expand (s1);
       /* We must allocate a new copy of the expanded string because
          variable_expand re-uses the same buffer.  */
@@ -1894,7 +1983,7 @@ record_target_var (struct nameseq *filenames, char *defn,
           initialize_file_variables (f, 1);
 
           current_variable_set_list = f->variables;
-          v = try_variable_definition (flocp, defn, origin, 1);
+          v = try_variable_definition (flocp, defn, origin, 1, NULL);
           if (!v)
             O (fatal, flocp, _("Malformed target-specific variable 
definition"));
           current_variable_set_list = global;
@@ -2899,7 +2988,7 @@ construct_include_path (const char **arg_dirs)
 
   for (cpp = dirs; *cpp != 0; ++cpp)
     do_variable_definition (NILF, ".INCLUDE_DIRS", *cpp,
-                            o_default, f_append, 0);
+                            o_default, f_append, 0, NULL);
 
   include_directories = dirs;
 }
-- 
1.9.1




reply via email to

[Prev in Thread] Current Thread [Next in Thread]