This is the mail archive of the gdb-patches@sourceware.org mailing list for the GDB project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: Use external editor in 'commands' command


2009/1/14 Eli Zaretskii <eliz@gnu.org>
>
> > Date: Wed, 14 Jan 2009 19:47:50 -0200
> > From: Alfredo Ortega <ortegaalfredo@gmail.com>
> >
> > I have made a small patch to the 'commands' command to allow the use
> > of an external editor to add or modify commands. This is convenient if
> > you are dealing with many commands per breakpoint.
> > The editor follows the behavior of the 'edit' command (/bin/ex by
> > default, or the 'EDITOR' environment variable)
> >
> > Tested on i686-pc-linux-gnu, please tell me what do you think about it.
>
> If this is accepted, we will need a suitable patch for the manual.

I see. This updated patch contains my proposed documentation changes
to gdb.texinfo and refcard.tex. I hope that the patch format is
adequate
diff -upr OLD/gdb/breakpoint.c NEW/gdb/breakpoint.c
--- OLD/gdb/breakpoint.c	2009-01-14 17:46:26.000000000 -0200
+++ NEW/gdb/breakpoint.c	2009-01-14 19:32:40.000000000 -0200
@@ -585,14 +585,20 @@ condition_command (char *arg, int from_t
   error (_("No breakpoint number %d."), bnum);
 }
 
+#define COMMANDS_EDCOMMAND "edit"
+
 static void
 commands_command (char *arg, int from_tty)
 {
   struct breakpoint *b;
   char *p;
-  int bnum;
+  int bnum,fsize;
   struct command_line *l;
-
+  char vitmp[50];
+  char cmdline[100];
+  FILE *tmpstream=NULL;
+  char *editor;
+  
   /* If we allowed this, we would have problems with when to
      free the storage, if we change the commands currently
      being read from.  */
@@ -602,6 +608,41 @@ commands_command (char *arg, int from_tt
 
   p = arg;
   bnum = get_number (&p);
+  vitmp[0]=0;
+  /* Edit commands with external editor */
+  if (!strcmp(COMMANDS_EDCOMMAND,p))	{
+	/* Generates the temporal file name*/
+	/* vitmp = tempnam(NULL,".gdb"); this is more secure according to man mkstemp, but gcc complains... */
+	p=NULL;
+	strcpy(vitmp,"/tmp/.gdbXXXXXX");
+	if (mkstemp(vitmp)<0) return;
+	ALL_BREAKPOINTS (b)
+		if (b->number == bnum)
+			{
+			if (&b->commands)	{
+				/* commands exists, must dump them to the temporal file */
+				tmpstream=fopen(vitmp,"w");
+				l = b->commands;
+				while(l)	{
+					fsize=0;
+					fsize+=fwrite(l->line,1,strlen(l->line),tmpstream);
+					fsize+=fwrite("\n",1,strlen("\n"),tmpstream);
+					if (fsize<strlen(l->line)+1) {
+						fclose(tmpstream);
+						unlink(vitmp);
+						return;
+						};
+					l = l->next;
+					}
+				fclose(tmpstream);
+				}
+			/* Edit the file */
+			if ((editor = (char *) getenv ("EDITOR")) == NULL)
+				editor = "/bin/ex";
+			snprintf(cmdline,sizeof(cmdline),"%s \"%s\"",editor,vitmp);
+			if (system(cmdline)<0) return;
+    			}
+	}
 
   if (p && *p)
     error (_("Unexpected extra arguments following breakpoint number."));
@@ -609,17 +650,31 @@ commands_command (char *arg, int from_tt
   ALL_BREAKPOINTS (b)
     if (b->number == bnum)
       {
-	char *tmpbuf = xstrprintf ("Type commands for when breakpoint %d is hit, one per line.", 
+	if(vitmp[0])	{
+		/* redirect instream */
+		tmpstream=instream;
+		instream=fopen(vitmp,"r");
+		l = read_command_lines (NULL, from_tty, 1);
+		}
+	else	{
+		char *tmpbuf = xstrprintf ("Type commands for when breakpoint %d is hit, one per line.", 
 				 bnum);
-	struct cleanup *cleanups = make_cleanup (xfree, tmpbuf);
-	l = read_command_lines (tmpbuf, from_tty, 1);
-	do_cleanups (cleanups);
+		struct cleanup *cleanups = make_cleanup (xfree, tmpbuf);
+		l = read_command_lines (tmpbuf, from_tty, 1);
+		do_cleanups (cleanups);
+		}
 	free_command_lines (&b->commands);
 	b->commands = l;
 	breakpoints_changed ();
 	observer_notify_breakpoint_modified (b->number);
+	if(vitmp[0])	{
+		/* restore instream */
+		instream=tmpstream;
+		/* erase temporal file */
+		unlink(vitmp);
+		}
 	return;
-    }
+       }
   error (_("No breakpoint number %d."), bnum);
 }
 
@@ -8103,6 +8158,9 @@ Usage is `ignore N COUNT'."));
   add_com ("commands", class_breakpoint, commands_command, _("\
 Set commands to be executed when a breakpoint is hit.\n\
 Give breakpoint number as argument after \"commands\".\n\
+After the command number you can enter the `edit' keyword, and then you can \n\
+use the external editor to add or modify commands.\n\
+Uses EDITOR environment variable contents as editor (or ex as default).\n\
 With no argument, the targeted breakpoint is the last one set.\n\
 The commands themselves follow starting on the next line.\n\
 Type a line containing \"end\" to indicate the end of them.\n\
diff -upr OLD/gdb/doc/gdb.texinfo NEW/gdb/doc/gdb.texinfo
--- OLD/gdb/doc/gdb.texinfo	2009-01-14 17:46:18.000000000 -0200
+++ NEW/gdb/doc/gdb.texinfo	2009-01-14 22:21:29.000000000 -0200
@@ -3976,6 +3976,8 @@ follow it immediately with @code{end}; t
 With no @var{bnum} argument, @code{commands} refers to the last
 breakpoint, watchpoint, or catchpoint set (not to the breakpoint most
 recently encountered).
+@item commands @r{[}@var{bnum}@r{]} edit
+This spawns an external editor for adding or editing commands. the final  @code{end} is not necessary in this case. @xref{Choosing your Editor}.
 @end table
 
 Pressing @key{RET} as a means of repeating the last @value{GDBN} command is
@@ -5587,6 +5589,7 @@ Edit the file containing @var{function} 
 
 @end table
 
+@node Choosing your Editor
 @subsection Choosing your Editor
 You can customize @value{GDBN} to use any editor you want
 @footnote{
diff -upr OLD/gdb/doc/refcard.tex NEW/gdb/doc/refcard.tex
--- OLD/gdb/doc/refcard.tex	2009-01-14 17:46:18.000000000 -0200
+++ NEW/gdb/doc/refcard.tex	2009-01-14 22:21:35.000000000 -0200
@@ -355,10 +355,10 @@ delete when reached
 ignore {\it n} {\it count}&ignore breakpoint {\it n}, {\it count}
 times\cr
 \cr
-commands {\it n}\par
+commands {\it n} \opt{{\it edit}} \par
 \qquad \opt{\tt silent}\par
-\qquad {\it command-list}&execute GDB {\it command-list} every time breakpoint {\it n} is reached. \opt{{\tt silent} suppresses default
-display}\cr
+\qquad {\it command-list}&execute GDB {\it command-list} every time breakpoint {\it n} is reached. \opt{{\tt silent} suppresses default display}  \opt{{\tt edit} use external editor for commands}
+\cr
 end&end of {\it command-list}\cr
 \endsec
 

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]