]> git.puffer.fish Git - matthieu/frr.git/commitdiff
Quagga processes should not die if they read an unrecognized line in
authorDaniel Walton <dwalton@cumulusnetworks.com>
Tue, 28 Jul 2015 03:30:22 +0000 (20:30 -0700)
committerDaniel Walton <dwalton@cumulusnetworks.com>
Tue, 28 Jul 2015 03:30:22 +0000 (20:30 -0700)
their config file

Ticket: CM-6738
Reviewed By: Donald and Dinesh
Testing Done:

<DETAILED DESCRIPTION (REPLACE)>

lib/command.c
lib/vty.c
lib/vty.h
vtysh/vtysh.c
vtysh/vtysh.h
vtysh/vtysh_config.c

index b034369d98e8e89ec708b1e846490cfe8346abd9..d487ce4e73a47478ffe96e6b55a996a797a659ee 100644 (file)
@@ -2761,11 +2761,12 @@ cmd_execute_command_strict (vector vline, struct vty *vty,
   return cmd_execute_command_real(vline, FILTER_STRICT, vty, cmd);
 }
 
-/* Configration make from file. */
+/* Configuration make from file. */
 int
 config_from_file (struct vty *vty, FILE *fp)
 {
-  int ret;
+  int ret, error_ret=0;
+  int saved_node;
   vector vline;
 
   while (fgets (vty->buf, VTY_BUFSIZ, fp))
@@ -2778,24 +2779,42 @@ config_from_file (struct vty *vty, FILE *fp)
       /* Execute configuration command : this is strict match */
       ret = cmd_execute_command_strict (vline, vty, NULL);
 
-      /* Try again with setting node to CONFIG_NODE */
-      while (ret != CMD_SUCCESS && ret != CMD_WARNING
-            && ret != CMD_ERR_NOTHING_TODO && vty->node != CONFIG_NODE)
-       {
-         vty->node = node_parent(vty->node);
-         ret = cmd_execute_command_strict (vline, vty, NULL);
-       }
+      // Climb the tree and try the command again at each node
+      if (ret != CMD_SUCCESS && ret != CMD_WARNING &&
+          ret != CMD_ERR_NOTHING_TODO && vty->node != CONFIG_NODE) {
 
-      cmd_free_strvec (vline);
+          saved_node = vty->node;
 
-      if (ret != CMD_SUCCESS && ret != CMD_WARNING
-         && ret != CMD_ERR_NOTHING_TODO)
-       return ret;
+          while (ret != CMD_SUCCESS && ret != CMD_WARNING &&
+                 ret != CMD_ERR_NOTHING_TODO && vty->node != CONFIG_NODE) {
+              vty->node = node_parent(vty->node);
+              ret = cmd_execute_command_strict (vline, vty, NULL);
+          }
+
+          // If climbing the tree did not work then ignore the command and
+          // stay at the same node
+          if (ret != CMD_SUCCESS && ret != CMD_WARNING &&
+              ret != CMD_ERR_NOTHING_TODO) {
+              vty->node = saved_node;
+
+              if (!error_ret) {
+                  memcpy(vty->error_buf, vty->buf, VTY_BUFSIZ);
+                  error_ret = ret;
+              }
+          }
+      }
+
+      cmd_free_strvec (vline);
     }
+
+  if (error_ret) {
+      return error_ret;
+  }
+
   return CMD_SUCCESS;
 }
 
-/* Configration from terminal */
+/* Configuration from terminal */
 DEFUN (config_terminal,
        config_terminal_cmd,
        "configure terminal",
index 7ced104014ef7c930a4e6f24614386cd2aa82bec..890f47acb6106bdec9cf81d41579ccaee5e22fd4 100644 (file)
--- a/lib/vty.c
+++ b/lib/vty.c
@@ -322,6 +322,7 @@ vty_new ()
 
   new->obuf = buffer_new(0);   /* Use default buffer size. */
   new->buf = XCALLOC (MTYPE_VTY, VTY_BUFSIZ);
+  new->error_buf = XCALLOC (MTYPE_VTY, VTY_BUFSIZ);
   new->max = VTY_BUFSIZ;
 
   return new;
@@ -478,6 +479,7 @@ vty_ensure (struct vty *vty, int length)
     {
       vty->max *= 2;
       vty->buf = XREALLOC (MTYPE_VTY, vty->buf, vty->max);
+      vty->error_buf = XREALLOC (MTYPE_VTY, vty->error_buf, vty->max);
     }
 }
 
@@ -2195,6 +2197,9 @@ vty_close (struct vty *vty)
   if (vty->buf)
     XFREE (MTYPE_VTY, vty->buf);
 
+  if (vty->error_buf)
+    XFREE (MTYPE_VTY, vty->error_buf);
+
   /* Check configure. */
   vty_config_unlock (vty);
 
@@ -2243,16 +2248,14 @@ vty_read_file (FILE *confp)
       switch (ret)
        {
          case CMD_ERR_AMBIGUOUS:
-           fprintf (stderr, "Ambiguous command.\n");
+           fprintf (stderr, "\nAmbiguous command.");
            break;
          case CMD_ERR_NO_MATCH:
-           fprintf (stderr, "There is no such command.\n");
+           fprintf (stderr, "\nThere is no such command.");
            break;
        }
-      fprintf (stderr, "Error occured during reading below line.\n%s\n", 
-              vty->buf);
-      vty_close (vty);
-      exit (1);
+      fprintf (stderr, "\nError occured during reading below line.\n%s\n",
+              vty->error_buf);
     }
 
   vty_close (vty);
index bce6c80bf17c418ae45b778bd35b0aa733ac8daa..e3ca3db038d6113cb9a031c028bc6076884e7c8d 100644 (file)
--- a/lib/vty.h
+++ b/lib/vty.h
@@ -49,6 +49,9 @@ struct vty
   /* Command input buffer */
   char *buf;
 
+  /* Command input error buffer */
+  char *error_buf;
+
   /* Command cursor point */
   int cp;
 
index b1c9f453b6cc11e773f0bef8b2c46a6882abc9c8..d134c027b6539fe7745b3e2a6c3e782ac683bb54 100644 (file)
@@ -662,7 +662,7 @@ vtysh_mark_file (const char *filename)
 }
 
 /* Configration make from file. */
-int
+void
 vtysh_config_from_file (struct vty *vty, FILE *fp)
 {
   int ret;
@@ -707,14 +707,15 @@ vtysh_config_from_file (struct vty *vty, FILE *fp)
          else
            {
              save_node = vty->node;
-             vtysh_execute ("end");
-             vtysh_execute ("configure terminal");
              vty->node = CONFIG_NODE;
              ret = cmd_execute_command_strict (vline, vty, &cmd);
+
+              // If the command did not work at CONFIG_NODE either then ignore
+              // the command and go back to our previous node.
              if ((ret != CMD_SUCCESS) &&
                  (ret != CMD_SUCCESS_DAEMON) &&
                  (ret != CMD_WARNING))
-               vty->node = save_node;
+                vty->node = save_node;
            }
        }         
 
@@ -758,7 +759,6 @@ vtysh_config_from_file (struct vty *vty, FILE *fp)
          }
        }
     }
-  return CMD_SUCCESS;
 }
 
 /* We don't care about the point of the cursor when '?' is typed. */
index b7ad299e1876fa567c4071d7c14e5c7cbee9044f..36128eed03f243403c050c3b0820ee37b0de1222 100644 (file)
@@ -50,7 +50,7 @@ char *vtysh_prompt (void);
 
 void vtysh_config_write (void);
 
-int vtysh_config_from_file (struct vty *, FILE *);
+void vtysh_config_from_file (struct vty *, FILE *);
 
 int vtysh_mark_file(const char *filename);
 
index b60b83120c853a6814ad73f04a577b3b28f90d8b..47886ea4639b528df9f1efd9b3d79c406f913d04 100644 (file)
@@ -368,7 +368,6 @@ vtysh_config_dump (FILE *fp)
 static void
 vtysh_read_file (FILE *confp)
 {
-  int ret;
   struct vty *vty;
 
   vty = vty_new ();
@@ -380,28 +379,12 @@ vtysh_read_file (FILE *confp)
   vtysh_execute_no_pager ("configure terminal");
 
   /* Execute configuration file. */
-  ret = vtysh_config_from_file (vty, confp);
+  vtysh_config_from_file (vty, confp);
 
   vtysh_execute_no_pager ("end");
   vtysh_execute_no_pager ("disable");
 
   vty_close (vty);
-
-  if (ret != CMD_SUCCESS) 
-    {
-      switch (ret)
-       {
-       case CMD_ERR_AMBIGUOUS:
-         fprintf (stderr, "Ambiguous command.\n");
-         break;
-       case CMD_ERR_NO_MATCH:
-         fprintf (stderr, "There is no such command.\n");
-         break;
-       }
-      fprintf (stderr, "Error occured during reading below line.\n%s\n", 
-              vty->buf);
-      exit (1);
-    }
 }
 
 /* Read up configuration file from config_default_dir. */