changeset 3805:44386b0e53da

[project @ 2001-03-01 16:54:31 by jwe]
author jwe
date Thu, 01 Mar 2001 16:54:33 +0000
parents 4073be5aefa1
children ae32674080b0
files configure.in src/ChangeLog src/DLD-FUNCTIONS/debug.cc src/Makefile.in src/debug.cc src/input.cc src/lex.l src/ov-usr-fcn.h src/pt-bp.cc src/pt-bp.h src/pt-cell.h src/pt-mat.h src/pt.cc src/pt.h
diffstat 14 files changed, 470 insertions(+), 360 deletions(-) [+]
line wrap: on
line diff
--- a/configure.in	Wed Feb 28 08:38:39 2001 +0000
+++ b/configure.in	Thu Mar 01 16:54:33 2001 +0000
@@ -21,7 +21,7 @@
 ### Software Foundation, 59 Temple Place - Suite 330, Boston, MA
 ### 02111-1307, USA. 
 
-AC_REVISION($Revision: 1.341 $)
+AC_REVISION($Revision: 1.342 $)
 AC_PREREQ(2.9)
 AC_INIT(src/octave.cc)
 AC_CONFIG_HEADER(config.h)
@@ -853,8 +853,17 @@
 AC_ISC_POSIX
 AC_MINIX
 AC_AIX
-AC_CHECK_FUNC(getpwnam, , AC_CHECK_LIB(sun, getpwnam))
-AC_CHECK_FUNC(gethostname, , AC_CHECK_LIB(socket, gethostname))
+AC_CHECK_FUNCS(gethostname getpwnam)
+if test "$ac_cv_func_gethostname" = yes; then
+  true
+else
+  AC_CHECK_LIB(socket, gethostname)
+fi
+if test "$ac_cv_func_getpwnam" = yes; then
+  true
+else
+  AC_CHECK_LIB(sun, getpwnam)
+fi
 
 ### How big are ints and how are they oriented?  These could probably
 ### be eliminated in favor of run-time checks.
--- a/src/ChangeLog	Wed Feb 28 08:38:39 2001 +0000
+++ b/src/ChangeLog	Thu Mar 01 16:54:33 2001 +0000
@@ -1,5 +1,56 @@
 2001-02-28  John W. Eaton  <jwe@bevo.che.wisc.edu>
 
+	* pt.h (tree::break_statement): New static member.
+	(tree::break_function): Make const.
+	* pt.cc (tree::break_statement): Initialize here.
+	(tree::break_function): Make const.
+	* pb-bp.h (break_statement): Delete global varaible declaration.
+	* pt-bp.cc (break_statement): Delete global variable definition.
+
+	* pt-bp.h (tree_breakpoint::bp_list): Rename from lst.
+
+	* pt.h: Don't inlcude ov-usr-fcn.h.
+	Provide forward declaration of octave_user_function class.
+
+2001-02-28  Ben Sapp  <bsapp@lanl.gov>
+
+	* debug.cc (get_user_function): Simplify by using curr_function.
+	(Fdbg_where): New function.
+	(Fdbg_list): Now DLD_TEXT instead of DLD_FCN.
+	(Fdbg_set): Likewise.
+	(Fdbg_delete): Likewise. 
+
+	* pt-bp.h (break_statement): New global variable.
+	(MAYBE_DO_BREAKPOINT): Check for dbg_next and dbg_step.
+	Print line, column, and current statement.
+	* pt-bp.cc (break_statement): New global variable
+	(tree_breakpoint::visit_do_until_command): Return immediately if
+	we've already found the line.
+	(tree_breakpoint::visit_colon_expression): Set breakpoint info here.
+	(tree_breakpoint::visit_binary_expression): Recurse here when
+	checking for breakpoints.
+
+	* debug.cc: Move here from DLD-FUNCTIONS/debug.cc.
+	* Makefile.in (DIST_SRC): Add it to the list.
+	(DLD_XSRC): Delete it from the list.
+
+	* pt.h (tree::last_line, tree::break_function): New static members.
+	* pt.cc(tree::last_line, tree::break_function): Initialize them.
+
+	* pt-cell.h (tree_cell::tree_cell): Accept line and column info.
+	* pt-mat.h (tree_matrix::tree_matrix): Likewise.
+
+	* ov-usr-fcn.h (octave_user_function::sym_tab): Delete.
+
+	* input.cc (get_user_input): Handle dbg_next.
+	Set tree:break_function and tree::last_line when doing dbg_step.
+
+2001-02-28  John W. Eaton  <jwe@bevo.che.wisc.edu>
+
+	* lex.l (handle_string): Save line and column information in token.
+	(is_keyword): Save line and column information for plot style and
+	axes tokens.
+
 	* toplev.cc (main_loop): Set retval to non-zero value if error
 	occurs when not interactive.
 
--- a/src/DLD-FUNCTIONS/debug.cc	Wed Feb 28 08:38:39 2001 +0000
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,331 +0,0 @@
-/*
-
-Copyright (C) 2001 Ben Sapp
-
-This file is part of Octave.
-
-Octave is free software; you can redistribute it and/or modify it
-under the terms of the GNU General Public License as published by the
-Free Software Foundation; either version 2, or (at your option) any
-later version.
-
-Octave is distributed in the hope that it will be useful, but WITHOUT
-ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
-FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
-for more details.
-
-You should have received a copy of the GNU General Public License
-along with Octave; see the file COPYING.  If not, write to the Free
-Software Foundation, 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
-
-*/
-
-#ifdef HAVE_CONFIG_H
-#include <config.h>
-#endif
-
-#include "error.h"
-#include "input.h"
-#include "pager.h"
-#include "oct-obj.h"
-#include "utils.h"
-#include "parse.h"
-#include "symtab.h"
-#include "gripes.h"
-#include "ov.h"
-#include "ov-usr-fcn.h"
-#include "ov-fcn.h"
-#include "pt-pr-code.h"
-#include "pt-stmt.h"
-#include "toplev.h"
-#include "unwind-prot.h"
-#include "variables.h"
-#include "defun-dld.h"
-#include "defun-int.h"
-
-octave_user_function *
-get_user_function (std::string str = "")
-{
-  octave_user_function *dbg_fcn = NULL;
-
-  if (curr_sym_tab != top_level_sym_tab)
-    {
-      Array<symbol_record *> srs =  
-	top_level_sym_tab->symbol_list ("*",
-					symbol_record::USER_FUNCTION,
-					SYMTAB_ALL_SCOPES);
-      int len = srs.length ();
-      
-      for (int i = 0; i < len ; i++)
-	{
-	  symbol_record *ptr = srs(i);
-	  
-	  if (ptr && ptr->is_user_function ())
-	    {
-	      octave_value tmp = ptr->def ();
-	      octave_user_function *tmp_fcn
-		= static_cast<octave_user_function *> (tmp.function_value ());
-	      symbol_table *st = tmp_fcn->sym_table ();
-
-	      if (st == curr_sym_tab)
-		{
-		  dbg_fcn = tmp_fcn;
-		  break;
-		}
-	    }
-	}
-
-    }
-  else if (str.compare (""))
-    {
-      symbol_record *ptr = curr_sym_tab->lookup (str);
-      
-      if (ptr && ptr->is_user_function ())
-	{
-	  octave_value tmp = ptr->def ();
-	  dbg_fcn = static_cast<octave_user_function *> (tmp.function_value ());
-	}
-      else
-	{
-	  symbol_record *ptr = lookup_by_name (str, false);
-	  
-	  if (ptr && ptr->is_user_function ())
-	    {
-	      octave_value tmp = ptr->def ();
-	      dbg_fcn = static_cast<octave_user_function *> (tmp.function_value ());
-	    }
-	}
-    }
-
-  return dbg_fcn;
-}
-
-DEFUN_DLD (dbg_set, args, ,
-  "-*- texinfo -*-\n\
-@deftypefn {Loadable Function} {rline =} dbg_set (func, line)\n\
-Set a breakpoint in a function\n\
-@table @code\n\
-@item func\n\
-String representing the function name.  When already in debug\n\
-mode this should be left out and only the line should be given.\n\
-@item line\n\
-Line you would like the breakpoint to be set on\n\
-@end table\n\
-\n\
-The rline returned is the real line that the breakpoint was set at.\n\
-\n\
-@end deftypefn\n\
-@seealso{dbg_delete, dbg_list, dbg_cont}")
-{
-  octave_value_list retval;
-  int result = -1;
-  int nargin = args.length ();
-
-  if (nargin == 2)
-    { 
-      if (!args(0).is_string ())
-	{
-	  gripe_wrong_type_arg ("dbg_set", args(0));
-	  return retval;
-	}
-
-      std::string symbol_name = args(0).string_value ();
-      
-      if (!args(1).is_real_scalar ())
-	{
-	  gripe_wrong_type_arg ("dbg_set", args(1));
-	  return retval;
-	}
-
-      int line = int(args(1).double_value ());
-      octave_user_function *dbg_fcn = get_user_function (symbol_name);
-
-      if (dbg_fcn)
-	{
-	  tree_statement_list *cmds = dbg_fcn->body ();
-	  result = cmds->set_breakpoint (line);
-	}
-      else
-	error ("unable to find the function requested\n");
-    }
-  else if (nargin == 1)
-    {
-      if (!args(0).is_real_scalar ())
-	{
-	  gripe_wrong_type_arg ("dbg_set", args(1));
-	  return retval;
-	}
-
-      int line = int(args(0).double_value ());
-      octave_user_function *dbg_fcn = get_user_function ();
-      
-      if (dbg_fcn)
-	{
-	  tree_statement_list *cmds = dbg_fcn->body ();
-	  result = cmds->set_breakpoint (line);
-	}
-      else
-	error ("unable to find the function requested\n");	 
-    }
-  else
-    error ("one argument when in a function and two when not.\n");
-
-  retval = double(result);
-  return retval;
-}
-
-DEFUN_DLD (dbg_delete, args, ,
-  "-*- texinfo -*-\n\
-@deftypefn {Loadable Function} {} dbg_delete (func, line)\n\
-Delete a breakpoint in a function\n\
-@table @code\n\
-@item func\n\
-String representing the function name.  When already in debug\n\
-mode this should be left out and only the line should be given.\n\
-@item line\n\
-Line where you would like to remove the the breakpoint\n\
-@end table\n\
-No checking is done to make sure that the line you requested is really\n\
-a breakpoint.   If you get the wrong line nothing will happen.\n\
-@end deftypefn\n\
-@seealso{dbg_delete, dbg_list, dbg_cont}")
-{
-  octave_value_list retval;
-  int line = -1;
-  std::string symbol_name = "";
-  int nargin = args.length ();
-  
-  if ((nargin != 1) && (nargin != 2))
-    {
-      error ("need one or two arguements\n");
-      return retval;
-    }
-  
-  if (nargin == 2)
-    {
-      if (!args(0).is_string ())
-	{
-	  gripe_wrong_type_arg ("dbg_delete", args(0));
-	  return retval;
-	}
-
-      std::string symbol_name = args(0).string_value ();
-      
-      if (!args(1).is_real_scalar ())
-	{
-	  gripe_wrong_type_arg ("dbg_delete", args(1));
-	  return retval;
-	}
-
-      line = int(args(1).double_value ());
-    }
-  else if (nargin == 1)
-    {
-      if (!args(1).is_real_scalar ())
-	{
-	  gripe_wrong_type_arg ("dbg_delete", args(1));
-	  return retval;
-	}
-
-      line = int(args(1).double_value ());      
-    }
-  else
-    {
-      error ("need one or two arguements\n");
-      return retval;
-    }
-
-  octave_user_function *dbg_fcn = get_user_function (symbol_name);
-  
-  if (dbg_fcn)
-    {
-      tree_statement_list *cmds = dbg_fcn->body ();
-      cmds->delete_breakpoint (line);
-    }
-  else
-    error ("unable to find the function requested\n");
-  return retval;
-}
-
-DEFUN_DLD (dbg_list, args, ,
-  "-*- texinfo -*-\n\
-@deftypefn {Loadable Function} {lst =} dbg_list ([func])\n\
-Return a vector containing the lines on which a function has \n\
-breakpoints set.\n\
-@table @code\n\
-@item func\n\
-String representing the function name.  When already in debug\n\
-mode this should be left out.\n\
-@end table\n\
-@end deftypefn\n\
-@seealso{dbg_delete, dbg_set, dbg_cont}")
-{
-  octave_value_list retval;
-  octave_value_list lst;
-  RowVector vec;
-  int nargin = args.length ();
-
-  if ((nargin != 0) && (nargin != 1))
-    {
-      error ("only zero or one arguements accepted\n");
-      return retval;
-    }
-
-  std::string symbol_name = "";
-
-  if (nargin == 1)
-    {
-      if (args(0).is_string ())
-	symbol_name = args(0).string_value ();
-      else
-	gripe_wrong_type_arg ("dbg_list", args(0));
-    }
-
-  octave_user_function *dbg_fcn = get_user_function (symbol_name);
- 
-  if (dbg_fcn)
-    {
-      tree_statement_list *cmds = dbg_fcn->body ();
-      lst = cmds->list_breakpoints ();
-      vec = RowVector (lst.length (), 0.0);
-
-      for (int i = 0; i < lst.length (); i++)
-	{ 
-	  if(lst(i).is_real_scalar ())
-	    {
-	      double x = lst(i).double_value ();
-
-	      if (! error_state)
-		vec(i) = x;
-	      else
-		panic_impossible ();
-	    }
-	  else
-	    panic_impossible ();
-	}
-    }
-  else
-    error ("unable to find the function you requested");
-
-  return octave_value(vec);
-}
-
-
-DEFUN_DLD (dbg_where, , ,
-  "-*- texinfo -*-\n\
-@deftypefn {Loadable Function} {} dbg_where ()\n\
-Show where we are in the code\n\
-@end deftypefn\n")
-{
-  octave_value retval;
-
-  warning ("not implemented");
-
-  return retval;
-}
-
-/*
-;;; Local Variables: ***
-;;; mode: C++ ***
-;;; End: ***
-*/
--- a/src/Makefile.in	Wed Feb 28 08:38:39 2001 +0000
+++ b/src/Makefile.in	Thu Mar 01 16:54:33 2001 +0000
@@ -40,7 +40,7 @@
 endif
 
 DLD_XSRC := balance.cc besselj.cc betainc.cc chol.cc colloc.cc dassl.cc \
-	debug.cc det.cc eig.cc expm.cc fft.cc fft2.cc filter.cc find.cc \
+	det.cc eig.cc expm.cc fft.cc fft2.cc filter.cc find.cc \
 	fsolve.cc gammainc.cc getgrent.cc getpwent.cc getrusage.cc \
 	givens.cc hess.cc ifft.cc ifft2.cc inv.cc log.cc lpsolve.cc \
 	lsode.cc lu.cc minmax.cc pinv.cc qr.cc quad.cc qz.cc rand.cc \
@@ -122,7 +122,7 @@
 
 DIST_SRC := BaseSLList.cc Cell.cc DLList.cc Map.cc SLList.cc \
 	SLStack.cc Stack.cc c-file-ptr-stream.cc comment-list.cc \
-	cutils.c data.cc \
+	cutils.c data.cc debug.cc \
 	defaults.cc defun.cc dirfns.cc dynamic-ld.cc error.cc \
 	file-io.cc fn-cache.cc gripes.cc help.cc input.cc lex.l \
 	load-save.cc mappers.cc matherr.c oct-fstrm.cc oct-hist.cc \
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/debug.cc	Thu Mar 01 16:54:33 2001 +0000
@@ -0,0 +1,317 @@
+/*
+
+Copyright (C) 2001 Ben Sapp
+
+This file is part of Octave.
+
+Octave is free software; you can redistribute it and/or modify it
+under the terms of the GNU General Public License as published by the
+Free Software Foundation; either version 2, or (at your option) any
+later version.
+
+Octave is distributed in the hope that it will be useful, but WITHOUT
+ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You should have received a copy of the GNU General Public License
+along with Octave; see the file COPYING.  If not, write to the Free
+Software Foundation, 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
+
+*/
+
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#include "defun.h"
+#include "error.h"
+#include "input.h"
+#include "pager.h"
+#include "oct-obj.h"
+#include "utils.h"
+#include "parse.h"
+#include "symtab.h"
+#include "gripes.h"
+#include "ov.h"
+#include "ov-usr-fcn.h"
+#include "ov-fcn.h"
+#include "pt-pr-code.h"
+#include "pt.h"
+#include "pt-bp.h"
+#include "pt-stmt.h"
+#include "toplev.h"
+#include "unwind-prot.h"
+#include "variables.h"
+
+octave_user_function *
+get_user_function (std::string str = "")
+{
+  octave_user_function *dbg_fcn = NULL;
+
+  if (curr_function)
+    {
+      dbg_fcn = curr_function;
+    }
+  else if (str.compare (""))
+    {
+      symbol_record *ptr = curr_sym_tab->lookup (str);
+      
+      if (ptr && ptr->is_user_function ())
+	{
+	  octave_value tmp = ptr->def ();
+	  dbg_fcn = static_cast<octave_user_function *> (tmp.function_value ());
+	}
+      else
+	{
+	  symbol_record *ptr = lookup_by_name (str, false);
+	  
+	  if (ptr && ptr->is_user_function ())
+	    {
+	      octave_value tmp = ptr->def ();
+	      dbg_fcn = static_cast<octave_user_function *> (tmp.function_value ());
+	    }
+	}
+    }
+
+  return dbg_fcn;
+}
+
+DEFUN_TEXT (dbg_set, args, ,
+  "-*- texinfo -*-\n\
+@deftypefn {Loadable Function} {rline =} dbg_set (func, line)\n\
+Set a breakpoint in a function\n\
+@table @code\n\
+@item func\n\
+String representing the function name.  When already in debug\n\
+mode this should be left out and only the line should be given.\n\
+@item line\n\
+Line you would like the breakpoint to be set on\n\
+@end table\n\
+\n\
+The rline returned is the real line that the breakpoint was set at.\n\
+\n\
+@end deftypefn\n\
+@seealso{dbg_delete, dbg_list, dbg_where}")
+{
+  octave_value retval;
+
+  int result = -1;
+  int nargin = args.length ();
+  
+  string_vector argv = args.make_argv ("dbg_set");
+
+  if (error_state)
+    return retval;
+
+  if (nargin == 2)
+    { 
+      std::string symbol_name = argv[1];
+
+      std::string line_number = argv[2];
+
+      int line = atoi (line_number.c_str ());
+      
+      octave_user_function *dbg_fcn = get_user_function (symbol_name);
+
+      if (dbg_fcn)
+	{
+	  tree_statement_list *cmds = dbg_fcn->body ();
+	  result = cmds->set_breakpoint (line);
+	}
+      else
+	error ("unable to find the function requested\n");
+    }
+  else if (nargin == 1)
+    {
+      std::string line_number = argv[1];
+
+      int line = atoi (line_number.c_str ());
+
+      octave_user_function *dbg_fcn = get_user_function ();
+      
+      if (dbg_fcn)
+	{
+	  tree_statement_list *cmds = dbg_fcn->body ();
+	  result = cmds->set_breakpoint (line);
+	}
+      else
+	error ("unable to find the function requested\n");	 
+    }
+  else
+    error ("one argument when in a function and two when not\n");
+
+  retval = static_cast<double> (result);
+
+  return retval;
+}
+
+DEFUN_TEXT (dbg_delete, args, ,
+  "-*- texinfo -*-\n\
+@deftypefn {Loadable Function} {} dbg_delete (func, line)\n\
+Delete a breakpoint in a function\n\
+@table @code\n\
+@item func\n\
+String representing the function name.  When already in debug\n\
+mode this should be left out and only the line should be given.\n\
+@item line\n\
+Line where you would like to remove the the breakpoint\n\
+@end table\n\
+No checking is done to make sure that the line you requested is really\n\
+a breakpoint.   If you get the wrong line nothing will happen.\n\
+@end deftypefn\n\
+@seealso{dbg_set, dbg_list, dbg_where}")
+{
+  octave_value retval;
+
+  std::string symbol_name = "";
+
+  int line = -1;
+  int nargin = args.length ();
+  
+  if (nargin != 1 && nargin != 2)
+    {
+      error ("need one or two arguements\n");
+      return retval;
+    }
+  
+  string_vector argv = args.make_argv ("dbg_delete");
+
+  if (error_state)
+    return retval;
+
+  if (nargin == 2)
+    {
+      octave_stdout << "2 input arguments\n";
+      symbol_name = argv[1];
+ 
+      octave_stdout << argv[1] << std::endl;
+      std::string line_number = argv[2];
+
+      line = atoi (line_number.c_str ());     
+    }
+  else if (nargin == 1)
+    {
+      octave_stdout << "1 input argument\n";
+      std::string line_number = argv[1];
+
+      line = atoi (line_number.c_str ());     
+    }
+  else
+    {
+      error ("need one or two arguements\n");
+      return retval;
+    }
+
+  octave_stdout << "symbol_name = " << symbol_name << std::endl;
+  octave_user_function *dbg_fcn = get_user_function (symbol_name);
+  
+  if (dbg_fcn)
+    {
+      tree_statement_list *cmds = dbg_fcn->body ();
+      cmds->delete_breakpoint (line);
+    }
+  else
+    error ("unable to find the function requested\n");
+
+  return retval;
+}
+
+DEFUN_TEXT (dbg_list, args, ,
+  "-*- texinfo -*-\n\
+@deftypefn {Loadable Function} {lst =} dbg_list ([func])\n\
+Return a vector containing the lines on which a function has \n\
+breakpoints set.\n\
+@table @code\n\
+@item func\n\
+String representing the function name.  When already in debug\n\
+mode this should be left out.\n\
+@end table\n\
+@end deftypefn\n\
+@seealso{dbg_delete, dbg_set, dbg_where}")
+{
+  octave_value retval;
+
+  int nargin = args.length ();
+
+  if (nargin != 0 && nargin != 1)
+    {
+      error ("only zero or one arguements accepted\n");
+      return retval;
+    }
+
+  std::string symbol_name = "";
+
+  if (nargin == 1)
+    {
+      if (args(0).is_string ())
+	symbol_name = args(0).string_value ();
+      else
+	gripe_wrong_type_arg ("dbg_list", args(0));
+    }
+
+  octave_user_function *dbg_fcn = get_user_function (symbol_name);
+ 
+  if (dbg_fcn)
+    {
+      tree_statement_list *cmds = dbg_fcn->body ();
+
+      octave_value_list lst = cmds->list_breakpoints ();
+
+      RowVector vec (lst.length (), 0.0);
+
+      for (int i = 0; i < lst.length (); i++)
+	{ 
+	  vec(i) = lst(i).double_value ();
+
+	  if (error_state)
+	    panic_impossible ();
+	}
+
+      retval = octave_value (vec);
+    }
+  else
+    error ("unable to find the function you requested\n");
+
+  return retval;
+}
+
+
+DEFUN_TEXT (dbg_where, , ,
+  "-*- texinfo -*-\n\
+@deftypefn {Loadable Function} {} dbg_where ()\n\
+Show where we are in the code\n\
+@end deftypefn\n\
+@seealso{dbg_delete, dbg_list, dbg_set}")
+{
+  octave_value retval;
+  
+  octave_user_function *dbg_fcn = curr_function;
+
+  if (dbg_fcn)
+    {
+      std::string name = dbg_fcn->function_name ();
+
+      octave_stdout << name << ":";
+
+      const tree *dbg_stmt = tree::break_statement;
+
+      if (dbg_stmt)
+	{
+	  octave_stdout << "line " << dbg_stmt->line () << ", "; 
+	  octave_stdout << "column " << dbg_stmt->column () << std::endl;
+	}
+      else
+	octave_stdout << "-1\n";
+    }
+  else
+    error ("must be inside of a user function to use dbg_where\n");
+
+  return retval;
+}
+
+/*
+;;; Local Variables: ***
+;;; mode: C++ ***
+;;; End: ***
+*/
--- a/src/input.cc	Wed Feb 28 08:38:39 2001 +0000
+++ b/src/input.cc	Thu Mar 01 16:54:33 2001 +0000
@@ -60,6 +60,7 @@
 #include "pathlen.h"
 #include "pt.h"
 #include "pt-const.h"
+#include "pt-stmt.h"
 #include "sighandlers.h"
 #include "symtab.h"
 #include "sysdep.h"
@@ -553,6 +554,21 @@
 	  else if (match_sans_spaces ("dbg_step", input_buf))
 	    {
 	      tree::break_next = true;
+
+	      tree::last_line = 0;
+
+	      tree::break_function = curr_function;
+
+	      return retval;
+	    }
+	  else if (match_sans_spaces ("dbg_next", input_buf))
+	    {
+	      tree::break_next = true;
+
+	      tree::last_line = curr_statement->line ();
+
+	      tree::break_function = curr_function;
+
 	      return retval;
 	    }
 	}
--- a/src/lex.l	Wed Feb 28 08:38:39 2001 +0000
+++ b/src/lex.l	Thu Mar 01 16:54:33 2001 +0000
@@ -990,6 +990,9 @@
 static int
 is_keyword (const std::string& s)
 {
+  int l = input_line_number;
+  int c = current_input_column;
+
   if (lexer_flags.plotting)
     {
       if (lexer_flags.in_plot_style)
@@ -999,7 +1002,7 @@
 	  if (! sty.empty ())
 	    {
 	      lexer_flags.in_plot_style = false;
-	      yylval.tok_val = new token (sty);
+	      yylval.tok_val = new token (sty, l, c);
 	      token_stack.push (yylval.tok_val);
 	      return STYLE;
 	    }
@@ -1011,16 +1014,13 @@
 	  if (! axes.empty ())
 	    {
 	      lexer_flags.in_plot_axes = false;
-	      yylval.tok_val = new token (axes);
+	      yylval.tok_val = new token (axes, l, c);
 	      token_stack.push (yylval.tok_val);
 	      return AXES_TAG;
 	    }
 	}	
     }
 
-  int l = input_line_number;
-  int c = current_input_column;
-
   int len = s.length ();
 
   const octave_kw *kw = octave_kw_lookup (s.c_str (), len);
@@ -1885,6 +1885,9 @@
 {
   std::ostrstream buf;
 
+  int bos_line = input_line_number;
+  int bos_col = current_input_column;
+
   int c;
   int escape_pending = 0;
 
@@ -1949,7 +1952,7 @@
 		      lexer_flags.convert_spaces_to_comma = true;
 		    }
 
-		  yylval.tok_val = new token (s);
+		  yylval.tok_val = new token (s, bos_line, bos_col);
 		  token_stack.push (yylval.tok_val);
 
 		  if (delim == '\'')
--- a/src/ov-usr-fcn.h	Wed Feb 28 08:38:39 2001 +0000
+++ b/src/ov-usr-fcn.h	Thu Mar 01 16:54:33 2001 +0000
@@ -133,8 +133,6 @@
 
   octave_comment_list *trailing_comment (void) { return trail_comm; }
 
-  symbol_table *sym_table (void) { return sym_tab; }
-
   void accept (tree_walker& tw);
 
 private:
--- a/src/pt-bp.cc	Wed Feb 28 08:38:39 2001 +0000
+++ b/src/pt-bp.cc	Thu Mar 01 16:54:33 2001 +0000
@@ -51,7 +51,7 @@
     {
       if (tr.is_breakpoint ())
 	{
-	  lst.append (octave_value (static_cast<double> (tr.line ())));
+	  bp_list.append (octave_value (static_cast<double> (tr.line ())));
 	  line = tr.line () + 1;
 	}
     }
@@ -84,11 +84,14 @@
 void
 tree_breakpoint::visit_do_until_command (tree_do_until_command& cmd)
 {
-  tree_statement_list *lst = cmd.body ();
+  if (found)
+    return;
 
   if (cmd.line () >= line)
     take_action (cmd);
 
+  tree_statement_list *lst = cmd.body ();
+
   if (lst)
     lst->accept (*this);
 
@@ -126,13 +129,10 @@
   tree_expression *rhs = expr.rhs ();
 
   if (lhs && lhs->line () >= line)
-    {
-      take_action (expr);
-      return;
-    }
+    lhs->accept (*this);
 
   if (rhs && rhs->line () >= line)
-    take_action (expr);  
+    rhs->accept (*this);  
 }
 
 void 
@@ -151,6 +151,9 @@
   if (found)
     return;
 
+  if (expr.line () >= line)
+    take_action (expr);
+
   tree_expression *base = expr.base (); 
 
   if (base)
--- a/src/pt-bp.h	Wed Feb 28 08:38:39 2001 +0000
+++ b/src/pt-bp.h	Thu Mar 01 16:54:33 2001 +0000
@@ -28,7 +28,10 @@
 #endif
 
 #include "input.h"
+#include "ov-usr-fcn.h"
 #include "pt-walk.h"
+#include "pt-pr-code.h"
+#include "toplev.h"
 
 class tree;
 
@@ -40,7 +43,7 @@
   enum action { set = 1, clear = 2, list = 3 };
 
   tree_breakpoint (int l, action a)
-    : line (l), act (a), found (false), lst () { }
+    : line (l), act (a), found (false), bp_list () { }
 
   ~tree_breakpoint (void) { }
 
@@ -140,7 +143,7 @@
 
   void visit_unwind_protect_command (tree_unwind_protect_command&);
 
-  octave_value_list get_list (void) { return lst; }
+  octave_value_list get_list (void) { return bp_list; }
   
   int get_line (void) { return line; }
 
@@ -148,13 +151,17 @@
 
   void take_action (tree &tr);
 
+  // Statement line number we are looking for.
   int line;
 
+  // What to do.
   action act;
-  
+
+  // Have we already found the line?
   bool found;
 
-  octave_value_list lst;
+  // List of breakpoint line numbers.
+  octave_value_list bp_list;
 
   // No copying!
 
@@ -166,10 +173,28 @@
 #define MAYBE_DO_BREAKPOINT \
   do \
     { \
-      if (tree::break_next || is_breakpoint ()) \
+      if ((tree::break_next && tree::last_line == 0) \
+	  || (tree::break_next \
+	      && curr_function == tree::break_function \
+	      && tree::last_line != line ()) \
+	  || is_breakpoint ()) \
         { \
           tree::break_next = false; \
-          octave_stdout << "line: " << line () << std::endl; \
+ \
+          if (curr_function) \
+            octave_stdout << curr_function->function_name () << ": ";  \
+ \
+          octave_stdout << "line " << line () << ", " \
+			<< "column " << column () \
+			<< std::endl; \
+ \
+          tree_print_code tpc (octave_stdout); \
+          this->accept (tpc); \
+ \
+          octave_stdout << std::endl; \
+ \
+          tree::break_statement = this; \
+ \
           do_keyboard (); \
         } \
     } \
--- a/src/pt-cell.h	Wed Feb 28 08:38:39 2001 +0000
+++ b/src/pt-cell.h	Thu Mar 01 16:54:33 2001 +0000
@@ -46,7 +46,7 @@
 {
 public:
 
-  tree_cell (tree_argument_list *row = 0) : tree_matrix (row) { }
+  tree_cell (tree_argument_list *row = 0, int line = -1, int column = -1) : tree_matrix (row, line, column) { }
 
   ~tree_cell (void) { }
 
--- a/src/pt-mat.h	Wed Feb 28 08:38:39 2001 +0000
+++ b/src/pt-mat.h	Thu Mar 01 16:54:33 2001 +0000
@@ -47,8 +47,8 @@
 {
 public:
 
-  tree_matrix (tree_argument_list *row = 0)
-    : tree_expression (), SLList<tree_argument_list *> ()
+  tree_matrix (tree_argument_list *row = 0, int line = -1, int column = -1)
+    : tree_expression (line, column), SLList<tree_argument_list *> ()
   {
     if (row)
       append (row);
--- a/src/pt.cc	Wed Feb 28 08:38:39 2001 +0000
+++ b/src/pt.cc	Thu Mar 01 16:54:33 2001 +0000
@@ -38,6 +38,15 @@
 // If true, stop executing at the next possible point.
 bool tree::break_next = false;
 
+// The line where dbg_next was executed.
+int tree::last_line = 0;
+
+// The function where the last breakpoint occurred.
+const octave_user_function *tree::break_function = 0;
+
+// The statement where the last breakpoint occurred.
+const tree *break_statement = 0;
+
 // Hide the details of the string buffer so that we are less likely to
 // create a memory leak.
 
--- a/src/pt.h	Wed Feb 28 08:38:39 2001 +0000
+++ b/src/pt.h	Thu Mar 01 16:54:33 2001 +0000
@@ -31,6 +31,7 @@
 
 #include <iostream>
 
+class octave_user_function;
 class tree_walker;
 
 // Base class for the parse tree.
@@ -69,6 +70,15 @@
 
   // If true, stop executing at the next possible point.
   static bool break_next;
+  
+  // The line where dbg_next was executed.
+  static int last_line; 
+
+  // The function where the last breakpoint occurred.
+  static const octave_user_function *break_function;
+
+  // The statement where the last breakpoint occurred.
+  static const tree *break_statement;
 
 private: