+2018-07-31 Alexandre Oliva <oliva@adacore.com>
+ Olivier Hainque <hainque@adacore.com>
+
+ * debug.h (decl_to_instance_map_t): New type.
+ (decl_to_instance_map): Declare.
+ (maybe_create_decl_to_instance_map): New inline function.
+ * final.c (bb_discriminator, last_bb_discriminator): New statics,
+ to track basic block discriminators.
+ (final_start_function_1): Initialize them.
+ (final_scan_insn_1): On NOTE_INSN_BASIC_BLOCK, track
+ bb_discriminator.
+ (decl_to_instance_map): New variable.
+ (map_decl_to_instance, maybe_set_discriminator): New functions.
+ (notice_source_line): Set discriminator.
+
2018-07-31 Ian Lance Taylor <iant@golang.org>
* targhooks.c (default_have_speculation_safe_value): Add
+2018-07-31 Alexandre Oliva <oliva@adacore.com>
+ Olivier Hainque <hainque@adacore.com>
+
+ * trans.c: Include debug.h.
+ (file_map): New static variable.
+ (gigi): Set it. Create decl_to_instance_map when needed.
+ (Subprogram_Body_to_gnu): Pass gnu_subprog_decl to...
+ (Sloc_to_locus): ... this. Add decl parm, map it to instance.
+ * gigi.h (Sloc_to_locus): Adjust declaration.
+
2018-07-31 Arnaud Charlet <charlet@adacore.com>
* clean.adb, gnatchop.adb, gnatfind.adb, gnatls.adb,
location and false if it doesn't. If CLEAR_COLUMN is true, set the column
information to 0. */
extern bool Sloc_to_locus (Source_Ptr Sloc, location_t *locus,
- bool clear_column = false);
+ bool clear_column = false, const_tree decl = 0);
/* Post an error message. MSG is the error message, properly annotated.
NODE is the node at which to post the error and the node to use for the
#include "stmt.h"
#include "varasm.h"
#include "output.h"
+#include "debug.h"
#include "libfuncs.h" /* For set_stack_check_libfunc. */
#include "tree-iterator.h"
#include "gimplify.h"
static const char *extract_encoding (const char *) ATTRIBUTE_UNUSED;
static const char *decode_name (const char *) ATTRIBUTE_UNUSED;
\f
+/* This makes gigi's file_info_ptr visible in this translation unit,
+ so that Sloc_to_locus can look it up when deciding whether to map
+ decls to instances. */
+
+static struct File_Info_Type *file_map;
+
/* This is the main program of the back-end. It sets up all the table
structures and then generates code. */
type_annotate_only = (gigi_operating_mode == 1);
+ if (Generate_SCO_Instance_Table != 0)
+ {
+ file_map = file_info_ptr;
+ maybe_create_decl_to_instance_map (number_file);
+ }
+
for (i = 0; i < number_file; i++)
{
/* Use the identifier table to make a permanent copy of the filename as
}
/* Destroy ourselves. */
+ file_map = NULL;
destroy_gnat_decl ();
destroy_gnat_utils ();
}
/* Set the line number in the decl to correspond to that of the body. */
- if (!Sloc_to_locus (Sloc (gnat_node), &locus))
+ if (!Sloc_to_locus (Sloc (gnat_node), &locus, false, gnu_subprog_decl))
locus = input_location;
DECL_SOURCE_LOCATION (gnu_subprog_decl) = locus;
return exp;
}
\f
-/* Convert SLOC into LOCUS. Return true if SLOC corresponds to a source code
- location and false if it doesn't. If CLEAR_COLUMN is true, set the column
- information to 0. */
+/* Convert SLOC into LOCUS. Return true if SLOC corresponds to a
+ source code location and false if it doesn't. If CLEAR_COLUMN is
+ true, set the column information to 0. If DECL is given and SLOC
+ refers to a File with an instance, map DECL to that instance. */
bool
-Sloc_to_locus (Source_Ptr Sloc, location_t *locus, bool clear_column)
+Sloc_to_locus (Source_Ptr Sloc, location_t *locus, bool clear_column,
+ const_tree decl)
{
if (Sloc == No_Location)
return false;
*locus
= linemap_position_for_line_and_column (line_table, map, line, column);
+ if (file_map && file_map[file - 1].Instance)
+ decl_to_instance_map->put (decl, file_map[file - 1].Instance);
+
return true;
}
extern const struct gcc_debug_hooks *
dump_go_spec_init (const char *, const struct gcc_debug_hooks *);
+/* Instance discriminator mapping table. See final.c. */
+typedef hash_map<const_tree, int> decl_to_instance_map_t;
+extern decl_to_instance_map_t *decl_to_instance_map;
+
+/* Allocate decl_to_instance_map with COUNT slots to begin wtih, if it
+ * hasn't been allocated yet. */
+
+static inline decl_to_instance_map_t *
+maybe_create_decl_to_instance_map (int count = 13)
+{
+ if (!decl_to_instance_map)
+ decl_to_instance_map = new decl_to_instance_map_t (count);
+ return decl_to_instance_map;
+}
+
#endif /* !GCC_DEBUG_H */
/* Column number of last NOTE. */
static int last_columnnum;
-/* Last discriminator written to assembly. */
+/* Discriminator written to assembly. */
static int last_discriminator;
-/* Discriminator of current block. */
+/* Discriminator to be written to assembly for current instruction.
+ Note: actual usage depends on loc_discriminator_kind setting. */
static int discriminator;
+/* Discriminator identifying current basic block among others sharing
+ the same locus. */
+static int bb_discriminator;
+
+/* Basic block discriminator for previous instruction. */
+static int last_bb_discriminator;
+
/* Highest line number in current block. */
static int high_block_linenum;
last_linenum = LOCATION_LINE (prologue_location);
last_columnnum = LOCATION_COLUMN (prologue_location);
last_discriminator = discriminator = 0;
+ last_bb_discriminator = bb_discriminator = 0;
high_block_linenum = high_function_linenum = last_linenum;
if (targetm.asm_out.unwind_emit)
targetm.asm_out.unwind_emit (asm_out_file, insn);
- discriminator = NOTE_BASIC_BLOCK (insn)->discriminator;
-
+ bb_discriminator = NOTE_BASIC_BLOCK (insn)->discriminator;
break;
case NOTE_INSN_EH_REGION_BEG:
}
\f
+
+/* Map DECLs to instance discriminators. This is allocated and
+ defined in ada/gcc-interfaces/trans.c, when compiling with -gnateS. */
+
+decl_to_instance_map_t *decl_to_instance_map;
+
+/* Return the instance number assigned to DECL. */
+
+static inline int
+map_decl_to_instance (const_tree decl)
+{
+ int *inst;
+
+ if (!decl_to_instance_map || !decl || !DECL_P (decl))
+ return 0;
+
+ inst = decl_to_instance_map->get (decl);
+
+ if (!inst)
+ return 0;
+
+ return *inst;
+}
+
+/* Set DISCRIMINATOR to the appropriate value, possibly derived from LOC. */
+
+static inline void
+maybe_set_discriminator (location_t loc)
+{
+ if (!decl_to_instance_map)
+ discriminator = bb_discriminator;
+ else
+ {
+ tree block = LOCATION_BLOCK (loc);
+
+ while (block && TREE_CODE (block) == BLOCK
+ && !inlined_function_outer_scope_p (block))
+ block = BLOCK_SUPERCONTEXT (block);
+
+ tree decl;
+
+ if (!block)
+ decl = current_function_decl;
+ else if (DECL_P (block))
+ decl = block;
+ else
+ decl = block_ultimate_origin (block);
+
+ discriminator = map_decl_to_instance (decl);
+ }
+}
+
/* Return whether a source line note needs to be emitted before INSN.
Sets IS_STMT to TRUE if the line should be marked as a possible
breakpoint location. */
filename = xloc.file;
linenum = xloc.line;
columnnum = xloc.column;
+ maybe_set_discriminator (loc);
force_source_line = true;
}
else if (override_filename)
filename = xloc.file;
linenum = xloc.line;
columnnum = xloc.column;
+ maybe_set_discriminator (INSN_LOCATION (insn));
}
else
{
+2018-07-31 Alexandre Oliva <oliva@adacore.com>
+ Olivier Hainque <hainque@adacore.com>
+
+ * gnat.dg/dinst.adb: New.
+ * gnat.dg/dinst_pkg.ads, gnat.dg/dinst_pkg.adb: New.
+
2018-07-31 David Malcolm <dmalcolm@redhat.com>
* gcc.dg/format/gcc_diag-1.c (foo): Update the %v tests for
--- /dev/null
+-- { dg-do compile { target *-*-gnu* } }
+-- { dg-options "-gnateS -gdwarf -g -O -gno-column-info" }
+-- { dg-final { scan-assembler "loc \[0-9] 5 \[0-9]( is_stmt \[0-9])? discriminator 1\n" } } */
+-- { dg-final { scan-assembler-not "loc \[0-9] 5 \[0-9]( is_stmt \[0-9])? discriminator 2\n" } } */
+-- { dg-final { scan-assembler "loc \[0-9] 5 \[0-9]( is_stmt \[0-9])? discriminator 3\n" } } */
+-- { dg-final { scan-assembler "loc \[0-9] 5 \[0-9]( is_stmt \[0-9])? discriminator 4\n" } } */
+
+
+with DInst_Pkg;
+procedure DInst is
+ package I1 is new DInst_Pkg; -- instance 1
+ package I2 is new DInst_Pkg; -- instance 2
+ package I3 is new DInst_Pkg; -- instance 3
+ package I4 is new DInst_Pkg; -- instance 4
+begin
+ I1.Foo;
+ -- I2.Foo;
+ I3.Foo;
+ I4.Foo;
+end;
--- /dev/null
+with Ada.Text_IO; use Ada.Text_IO;
+package body DInst_Pkg is
+ procedure Foo is
+ begin
+ Put_Line ("hello there");
+ end;
+end;
--- /dev/null
+generic
+package DInst_Pkg is
+ procedure Foo;
+end;