* dsrec.c (load_srec, make_srec): Use bfd_get_section_size instead of
[binutils-gdb.git] / gdb / stack.c
index ebf439e50e6bcd5e109e1e0ec373c95ee3d6159c..ac4434cd37cddd8dea404a8206fd90ab822a69bb 100644 (file)
@@ -1,8 +1,8 @@
 /* Print and select stack frames for GDB, the GNU debugger.
 
    Copyright 1986, 1987, 1988, 1989, 1990, 1991, 1992, 1993, 1994,
-   1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003 Free Software
-   Foundation, Inc.
+   1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004 Free
+   Software Foundation, Inc.
 
    This file is part of GDB.
 
@@ -44,6 +44,7 @@
 #include "gdb_assert.h"
 #include "dictionary.h"
 #include "reggroups.h"
+#include "regcache.h"
 
 /* Prototypes for exported functions. */
 
@@ -51,12 +52,10 @@ void args_info (char *, int);
 
 void locals_info (char *, int);
 
-void (*selected_frame_level_changed_hook) (int);
+void (*deprecated_selected_frame_level_changed_hook) (int);
 
 void _initialize_stack (void);
 
-void return_command (char *, int);
-
 /* Prototypes for local functions. */
 
 static void down_command (char *, int);
@@ -96,9 +95,9 @@ static int print_block_frame_locals (struct block *,
                                     struct ui_file *);
 
 static void print_frame (struct frame_info *fi, 
-                        int level, 
-                        int source
-                        int args, 
+                        int print_level, 
+                        enum print_what print_what
+                        int print_args, 
                         struct symtab_and_line sal);
 
 static void backtrace_command (char *, int);
@@ -121,42 +120,38 @@ int annotation_level = 0;
 struct print_stack_frame_args
   {
     struct frame_info *fi;
-    int level;
-    int source;
-    int args;
+    int print_level;
+    enum print_what print_what;
+    int print_args;
   };
 
 /* Show or print the frame arguments.
    Pass the args the way catch_errors wants them.  */
-static int print_stack_frame_stub (void *args);
 static int
 print_stack_frame_stub (void *args)
 {
   struct print_stack_frame_args *p = (struct print_stack_frame_args *) args;
 
-  print_frame_info (p->fi, p->level, p->source, p->args);
+  print_frame_info (p->fi, p->print_level, p->print_what, p->print_args);
   return 0;
 }
 
-/* Show or print a stack frame briefly.  FRAME_INFI should be the frame info
-   and LEVEL should be its level in the stack (or -1 for level not defined).
-   This prints the level, the function executing, the arguments,
-   and the file name and line number.
-   If the pc is not at the beginning of the source line,
-   the actual pc is printed at the beginning.
-
-   If SOURCE is 1, print the source line as well.
-   If SOURCE is -1, print ONLY the source line.  */
+/* Show or print a stack frame FI briefly.  The output is format
+   according to PRINT_LEVEL and PRINT_WHAT printing the frame's
+   relative level, function name, argument list, and file name and
+   line number.  If the frame's PC is not at the beginning of the
+   source line, the actual PC is printed at the beginning.  */
 
 void
-print_stack_frame (struct frame_info *fi, int level, int source)
+print_stack_frame (struct frame_info *fi, int print_level,
+                  enum print_what print_what)
 {
   struct print_stack_frame_args args;
 
   args.fi = fi;
-  args.level = level;
-  args.source = source;
-  args.args = 1;
+  args.print_level = print_level;
+  args.print_what = print_what;
+  args.print_args = 1;
 
   catch_errors (print_stack_frame_stub, (char *) &args, "", RETURN_MASK_ALL);
 }  
@@ -419,7 +414,8 @@ print_args_stub (void *args)
    LOC_AND_SRC: Print location and source line.  */
 
 void
-print_frame_info (struct frame_info *fi, int level, int source, int args)
+print_frame_info (struct frame_info *fi, int print_level,
+                 enum print_what print_what, int print_args)
 {
   struct symtab_and_line sal;
   int source_print;
@@ -431,14 +427,16 @@ print_frame_info (struct frame_info *fi, int level, int source, int args)
       struct cleanup *uiout_cleanup
        = make_cleanup_ui_out_tuple_begin_end (uiout, "frame");
 
-      annotate_frame_begin (level == -1 ? 0 : level, get_frame_pc (fi));
+      annotate_frame_begin (print_level ? frame_relative_level (fi) : 0,
+                           get_frame_pc (fi));
 
       /* Do this regardless of SOURCE because we don't have any source
          to list for this frame.  */
-      if (level >= 0)
+      if (print_level)
         {
           ui_out_text (uiout, "#");
-          ui_out_field_fmt_int (uiout, 2, ui_left, "level", level);
+          ui_out_field_fmt_int (uiout, 2, ui_left, "level",
+                               frame_relative_level (fi));
         }
       if (ui_out_is_mi_like_p (uiout))
         {
@@ -472,14 +470,14 @@ print_frame_info (struct frame_info *fi, int level, int source, int args)
      line containing fi->pc.  */
   find_frame_sal (fi, &sal);
 
-  location_print = (source == LOCATION 
-                   || source == LOC_AND_ADDRESS
-                   || source == SRC_AND_LOC);
+  location_print = (print_what == LOCATION 
+                   || print_what == LOC_AND_ADDRESS
+                   || print_what == SRC_AND_LOC);
 
   if (location_print || !sal.symtab)
-    print_frame (fi, level, source, args, sal);
+    print_frame (fi, print_level, print_what, print_args, sal);
 
-  source_print = (source == SRC_LINE || source == SRC_AND_LOC);
+  source_print = (print_what == SRC_LINE || print_what == SRC_AND_LOC);
 
   if (sal.symtab)
     set_current_source_symtab_and_line (&sal);
@@ -488,15 +486,16 @@ print_frame_info (struct frame_info *fi, int level, int source, int args)
     {
       struct symtab_and_line cursal;
       int done = 0;
-      int mid_statement = (source == SRC_LINE) && (get_frame_pc (fi) != sal.pc);
+      int mid_statement = ((print_what == SRC_LINE)
+                          && (get_frame_pc (fi) != sal.pc));
 
       if (annotation_level)
        done = identify_source_line (sal.symtab, sal.line, mid_statement,
                                     get_frame_pc (fi));
       if (!done)
        {
-         if (print_frame_info_listing_hook)
-           print_frame_info_listing_hook (sal.symtab, sal.line, sal.line + 1, 0);
+         if (deprecated_print_frame_info_listing_hook)
+           deprecated_print_frame_info_listing_hook (sal.symtab, sal.line, sal.line + 1, 0);
          else
            {
              /* We used to do this earlier, but that is clearly
@@ -523,7 +522,7 @@ print_frame_info (struct frame_info *fi, int level, int source, int args)
       set_current_source_symtab_and_line (&cursal);
     }
 
-  if (source != 0)
+  if (print_what != LOCATION)
     set_default_breakpoint (1, get_frame_pc (fi), sal.symtab, sal.line);
 
   annotate_frame_end ();
@@ -533,9 +532,9 @@ print_frame_info (struct frame_info *fi, int level, int source, int args)
 
 static void
 print_frame (struct frame_info *fi, 
-            int level, 
-            int source
-            int args, 
+            int print_level, 
+            enum print_what print_what
+            int print_args, 
             struct symtab_and_line sal)
 {
   struct symbol *func;
@@ -572,14 +571,6 @@ print_frame (struct frame_info *fi,
          && (SYMBOL_VALUE_ADDRESS (msymbol)
              > BLOCK_START (SYMBOL_BLOCK_VALUE (func))))
        {
-#if 0
-         /* There is no particular reason to think the line number
-            information is wrong.  Someone might have just put in
-            a label with asm() but left the line numbers alone.  */
-         /* In this case we have no way of knowing the source file
-            and line number, so don't print them.  */
-         sal.symtab = 0;
-#endif
          /* We also don't know anything about the function besides
             its address and name.  */
          func = 0;
@@ -623,19 +614,21 @@ print_frame (struct frame_info *fi,
        }
     }
 
-  annotate_frame_begin (level == -1 ? 0 : level, get_frame_pc (fi));
+  annotate_frame_begin (print_level ? frame_relative_level (fi) : 0,
+                       get_frame_pc (fi));
 
   list_chain = make_cleanup_ui_out_tuple_begin_end (uiout, "frame");
 
-  if (level >= 0)
+  if (print_level)
     {
       ui_out_text (uiout, "#");
-      ui_out_field_fmt_int (uiout, 2, ui_left, "level", level);
+      ui_out_field_fmt_int (uiout, 2, ui_left, "level",
+                           frame_relative_level (fi));
     }
   if (addressprint)
     if (get_frame_pc (fi) != sal.pc
        || !sal.symtab
-       || source == LOC_AND_ADDRESS)
+       || print_what == LOC_AND_ADDRESS)
       {
        annotate_frame_address ();
        ui_out_field_core_addr (uiout, "addr", get_frame_pc (fi));
@@ -650,7 +643,7 @@ print_frame (struct frame_info *fi,
   annotate_frame_args ();
       
   ui_out_text (uiout, " (");
-  if (args)
+  if (print_args)
     {
       struct print_args_args args;
       struct cleanup *args_list_chain;
@@ -941,13 +934,6 @@ frame_info (char *addr_exp, int from_tty)
   print_address_numeric (frame_pc_unwind (fi), 1, gdb_stdout);
   printf_filtered ("\n");
 
-  {
-    int frameless;
-    frameless = FRAMELESS_FUNCTION_INVOCATION (fi);
-    if (frameless)
-      printf_filtered (" (FRAMELESS),");
-  }
-
   if (calling_frame_info)
     {
       printf_filtered (" called by frame at ");
@@ -969,10 +955,6 @@ frame_info (char *addr_exp, int from_tty)
     printf_filtered (" source language %s.\n",
                     language_str (s->language));
 
-#ifdef PRINT_EXTRA_FRAME_INFO
-  PRINT_EXTRA_FRAME_INFO (fi);
-#endif
-
   {
     /* Address of the argument list for this frame, or 0.  */
     CORE_ADDR arg_list = get_frame_args_address (fi);
@@ -1055,7 +1037,7 @@ frame_info (char *addr_exp, int from_tty)
            /* NOTE: cagney/2003-05-22: This is assuming that the
                stack pointer was packed as an unsigned integer.  That
                may or may not be valid.  */
-           sp = extract_unsigned_integer (value, REGISTER_RAW_SIZE (SP_REGNUM));
+           sp = extract_unsigned_integer (value, DEPRECATED_REGISTER_RAW_SIZE (SP_REGNUM));
            printf_filtered (" Previous frame's sp is ");
            print_address_numeric (sp, 1, gdb_stdout);
            printf_filtered ("\n");
@@ -1106,33 +1088,6 @@ frame_info (char *addr_exp, int from_tty)
   }
 }
 
-#if 0
-/* Set a limit on the number of frames printed by default in a
-   backtrace.  */
-
-static int backtrace_limit;
-
-static void
-set_backtrace_limit_command (char *count_exp, int from_tty)
-{
-  int count = parse_and_eval_long (count_exp);
-
-  if (count < 0)
-    error ("Negative argument not meaningful as backtrace limit.");
-
-  backtrace_limit = count;
-}
-
-static void
-backtrace_limit_info (char *arg, int from_tty)
-{
-  if (arg)
-    error ("\"Info backtrace-limit\" takes no arguments.");
-
-  printf_unfiltered ("Backtrace limit: %d.\n", backtrace_limit);
-}
-#endif
-
 /* Print briefly all stack frames or just the innermost COUNT frames.  */
 
 static void backtrace_command_1 (char *count_exp, int show_locals,
@@ -1224,7 +1179,7 @@ backtrace_command_1 (char *count_exp, int show_locals, int from_tty)
          means further attempts to backtrace would fail (on the other
          hand, perhaps the code does or could be fixed to make sure
          the frame->prev field gets set to NULL in that case).  */
-      print_frame_info (fi, trailing_level + i, 0, 1);
+      print_frame_info (fi, 1, LOCATION, 1);
       if (show_locals)
        print_frame_local_vars (fi, 1, gdb_stdout);
     }
@@ -1357,7 +1312,7 @@ print_block_frame_labels (struct block *b, int *have_default,
 
   ALL_BLOCK_SYMBOLS (b, iter, sym)
     {
-      if (STREQ (DEPRECATED_SYMBOL_NAME (sym), "default"))
+      if (strcmp (DEPRECATED_SYMBOL_NAME (sym), "default") == 0)
        {
          if (*have_default)
            continue;
@@ -1511,10 +1466,6 @@ catch_info (char *ignore, int from_tty)
       /* Ideally, here we should interact with the C++ runtime
          system to find the list of active handlers, etc. */
       fprintf_filtered (gdb_stdout, "Info catch not supported with this target/compiler combination.\n");
-#if 0
-      if (!deprecated_selected_frame)
-       error ("No frame selected.");
-#endif
     }
   else
     {
@@ -1610,9 +1561,7 @@ select_and_print_frame (struct frame_info *fi)
 {
   select_frame (fi);
   if (fi)
-    {
-      print_stack_frame (fi, frame_relative_level (fi), 1);
-    }
+    print_stack_frame (fi, 1, SRC_AND_LOC);
 }
 \f
 /* Return the symbol-block in which the selected frame is executing.
@@ -1699,7 +1648,6 @@ void
 select_frame_command (char *level_exp, int from_tty)
 {
   struct frame_info *frame;
-  int level = frame_relative_level (deprecated_selected_frame);
 
   if (!target_has_stack)
     error ("No stack.");
@@ -1707,8 +1655,6 @@ select_frame_command (char *level_exp, int from_tty)
   frame = parse_frame_specification (level_exp);
 
   select_frame (frame);
-  if (level != frame_relative_level (deprecated_selected_frame))
-    selected_frame_level_changed_event (frame_relative_level (deprecated_selected_frame));
 }
 
 /* The "frame" command.  With no arg, print selected frame briefly.
@@ -1719,8 +1665,7 @@ void
 frame_command (char *level_exp, int from_tty)
 {
   select_frame_command (level_exp, from_tty);
-  print_stack_frame (deprecated_selected_frame,
-                    frame_relative_level (deprecated_selected_frame), 1);
+  print_stack_frame (get_selected_frame (), 1, SRC_AND_LOC);
 }
 
 /* The XDB Compatibility command to print the current frame. */
@@ -1730,8 +1675,7 @@ current_frame_command (char *level_exp, int from_tty)
 {
   if (target_has_stack == 0 || deprecated_selected_frame == 0)
     error ("No stack.");
-  print_stack_frame (deprecated_selected_frame,
-                         frame_relative_level (deprecated_selected_frame), 1);
+  print_stack_frame (get_selected_frame (), 1, SRC_AND_LOC);
 }
 
 /* Select the frame up one or COUNT stack levels
@@ -1753,7 +1697,6 @@ up_silently_base (char *count_exp)
   if (count1 != 0 && count_exp == 0)
     error ("Initial frame selected; you cannot go up.");
   select_frame (fi);
-  selected_frame_level_changed_event (frame_relative_level (deprecated_selected_frame));
 }
 
 static void
@@ -1766,8 +1709,7 @@ static void
 up_command (char *count_exp, int from_tty)
 {
   up_silently_base (count_exp);
-  print_stack_frame (deprecated_selected_frame,
-                    frame_relative_level (deprecated_selected_frame), 1);
+  print_stack_frame (get_selected_frame (), 1, SRC_AND_LOC);
 }
 
 /* Select the frame down one or COUNT stack levels
@@ -1798,7 +1740,6 @@ down_silently_base (char *count_exp)
     }
 
   select_frame (frame);
-  selected_frame_level_changed_event (frame_relative_level (deprecated_selected_frame));
 }
 
 static void
@@ -1811,102 +1752,150 @@ static void
 down_command (char *count_exp, int from_tty)
 {
   down_silently_base (count_exp);
-  print_stack_frame (deprecated_selected_frame,
-                    frame_relative_level (deprecated_selected_frame), 1);
+  print_stack_frame (get_selected_frame (), 1, SRC_AND_LOC);
 }
 \f
 void
 return_command (char *retval_exp, int from_tty)
 {
   struct symbol *thisfun;
-  CORE_ADDR selected_frame_addr;
-  CORE_ADDR selected_frame_pc;
-  struct frame_info *frame;
   struct value *return_value = NULL;
+  const char *query_prefix = "";
 
-  if (deprecated_selected_frame == NULL)
+  /* FIXME: cagney/2003-10-20: Perform a minimal existance test on the
+     target.  If that fails, error out.  For the moment don't rely on
+     get_selected_frame as it's error message is the the singularly
+     obscure "No registers".  */
+  if (!target_has_registers)
     error ("No selected frame.");
-  thisfun = get_frame_function (deprecated_selected_frame);
-  selected_frame_addr = get_frame_base (deprecated_selected_frame);
-  selected_frame_pc = get_frame_pc (deprecated_selected_frame);
-
-  /* Compute the return value (if any -- possibly getting errors here).  */
+  thisfun = get_frame_function (get_selected_frame ());
 
+  /* Compute the return value.  If the computation triggers an error,
+     let it bail.  If the return type can't be handled, set
+     RETURN_VALUE to NULL, and QUERY_PREFIX to an informational
+     message.  */
   if (retval_exp)
     {
       struct type *return_type = NULL;
 
+      /* Compute the return value.  Should the computation fail, this
+         call throws an error.  */
       return_value = parse_and_eval (retval_exp);
 
-      /* Cast return value to the return type of the function.  */
+      /* Cast return value to the return type of the function.  Should
+         the cast fail, this call throws an error.  */
       if (thisfun != NULL)
        return_type = TYPE_TARGET_TYPE (SYMBOL_TYPE (thisfun));
       if (return_type == NULL)
        return_type = builtin_type_int;
+      CHECK_TYPEDEF (return_type);
       return_value = value_cast (return_type, return_value);
 
-      /* Make sure we have fully evaluated it, since
-         it might live in the stack frame we're about to pop.  */
+      /* Make sure the value is fully evaluated.  It may live in the
+         stack frame we're about to pop.  */
       if (VALUE_LAZY (return_value))
        value_fetch_lazy (return_value);
-    }
 
-  /* If interactive, require confirmation.  */
-
-  if (from_tty)
-    {
-      if (thisfun != 0)
+      if (TYPE_CODE (return_type) == TYPE_CODE_VOID)
+       /* If the return-type is "void", don't try to find the
+           return-value's location.  However, do still evaluate the
+           return expression so that, even when the expression result
+           is discarded, side effects such as "return i++" still
+           occure.  */
+       return_value = NULL;
+      /* FIXME: cagney/2004-01-17: If the architecture implements both
+         return_value and extract_returned_value_address, should allow
+         "return" to work - don't set return_value to NULL.  */
+      else if (!gdbarch_return_value_p (current_gdbarch)
+              && (TYPE_CODE (return_type) == TYPE_CODE_STRUCT
+                  || TYPE_CODE (return_type) == TYPE_CODE_UNION))
        {
-         if (!query ("Make %s return now? ", SYMBOL_PRINT_NAME (thisfun)))
-           {
-             error ("Not confirmed.");
-             /* NOTREACHED */
-           }
+         /* NOTE: cagney/2003-10-20: Compatibility hack for legacy
+            code.  Old architectures don't expect STORE_RETURN_VALUE
+            to be called with with a small struct that needs to be
+            stored in registers.  Don't start doing it now.  */
+         query_prefix = "\
+A structure or union return type is not supported by this architecture.\n\
+If you continue, the return value that you specified will be ignored.\n";
+         return_value = NULL;
+       }
+      else if (using_struct_return (return_type, 0))
+       {
+         query_prefix = "\
+The location at which to store the function's return value is unknown.\n\
+If you continue, the return value that you specified will be ignored.\n";
+         return_value = NULL;
        }
-      else if (!query ("Make selected stack frame return now? "))
-       error ("Not confirmed.");
     }
 
-  /* FIXME: cagney/2003-01-18: Rather than pop each frame in turn,
-     this code should just go straight to the relevant frame and pop
-     that.  */
-
-  /* Do the real work.  Pop until the specified frame is current.  We
-     use this method because the deprecated_selected_frame is not
-     valid after a frame_pop().  The pc comparison makes this work
-     even if the selected frame shares its fp with another frame.  */
-
-  /* FIXME: cagney/32003-03-12: This code should use frame_id_eq().
-     Unfortunatly, that function doesn't yet include the PC in any
-     frame ID comparison.  */
+  /* Does an interactive user really want to do this?  Include
+     information, such as how well GDB can handle the return value, in
+     the query message.  */
+  if (from_tty)
+    {
+      int confirmed;
+      if (thisfun == NULL)
+       confirmed = query ("%sMake selected stack frame return now? ",
+                          query_prefix);
+      else
+       confirmed = query ("%sMake %s return now? ", query_prefix,
+                          SYMBOL_PRINT_NAME (thisfun));
+      if (!confirmed)
+       error ("Not confirmed");
+    }
 
-  while (selected_frame_addr != get_frame_base (frame = get_current_frame ())
-        || selected_frame_pc != get_frame_pc (frame))
-    frame_pop (get_current_frame ());
+  /* NOTE: cagney/2003-01-18: Is this silly?  Rather than pop each
+     frame in turn, should this code just go straight to the relevant
+     frame and pop that?  */
 
-  /* Then pop that frame.  */
+  /* First discard all frames inner-to the selected frame (making the
+     selected frame current).  */
+  {
+    struct frame_id selected_id = get_frame_id (get_selected_frame ());
+    while (!frame_id_eq (selected_id, get_frame_id (get_current_frame ())))
+      {
+       if (frame_id_inner (selected_id, get_frame_id (get_current_frame ())))
+         /* Caught in the safety net, oops!  We've gone way past the
+             selected frame.  */
+         error ("Problem while popping stack frames (corrupt stack?)");
+       frame_pop (get_current_frame ());
+      }
+  }
 
+  /* Second discard the selected frame (which is now also the current
+     frame).  */
   frame_pop (get_current_frame ());
 
-  /* Compute the return value (if any) and store in the place
-     for return values.  */
-
-  if (retval_exp)
-    set_return_value (return_value);
-
-  /* If we are at the end of a call dummy now, pop the dummy frame too.  */
+  /* Store RETURN_VAUE in the just-returned register set.  */
+  if (return_value != NULL)
+    {
+      struct type *return_type = VALUE_TYPE (return_value);
+      if (!gdbarch_return_value_p (current_gdbarch))
+       {
+         STORE_RETURN_VALUE (return_type, current_regcache,
+                             VALUE_CONTENTS (return_value));
+       }
+      /* FIXME: cagney/2004-01-17: If extract_returned_value_address
+         is available and the function is using
+         RETURN_VALUE_STRUCT_CONVENTION, should use it to find the
+         address of the returned value so that it can be assigned.  */
+      else
+       {
+         gdb_assert (gdbarch_return_value (current_gdbarch, return_type,
+                                           NULL, NULL, NULL)
+                     == RETURN_VALUE_REGISTER_CONVENTION);
+         gdbarch_return_value (current_gdbarch, return_type,
+                               current_regcache, NULL /*read*/,
+                               VALUE_CONTENTS (return_value) /*write*/);
+       }
+    }
 
-  /* FIXME: cagney/2003-01-18: This is silly.  Instead of popping all
-     the frames except the dummy, and then, as an afterthought,
-     popping the dummy frame, this code should just pop through to the
-     dummy frame.  */
-  
-  if (CALL_DUMMY_HAS_COMPLETED (read_pc(), read_sp (),
-                               get_frame_base (get_current_frame ())))
+  /* If we are at the end of a call dummy now, pop the dummy frame
+     too.  */
+  if (get_frame_type (get_current_frame ()) == DUMMY_FRAME)
     frame_pop (get_current_frame ());
 
   /* If interactive, print the frame that is now current.  */
-
   if (from_tty)
     frame_command ("0", 1);
   else
@@ -1984,7 +1973,14 @@ get_frame_language (void)
 
   if (deprecated_selected_frame)
     {
-      s = find_pc_symtab (get_frame_pc (deprecated_selected_frame));
+      /* We determine the current frame language by looking up its
+         associated symtab.  To retrieve this symtab, we use the frame PC.
+         However we cannot use the frame pc as is, because it usually points
+         to the instruction following the "call", which is sometimes the first
+         instruction of another function.  So we rely on
+         get_frame_address_in_block(), it provides us with a PC which is
+         guaranteed to be inside the frame's code block.  */
+      s = find_pc_symtab (get_frame_address_in_block (deprecated_selected_frame));
       if (s)
        flang = s->language;
       else