Re: Stop Gas from generating line info or address ranges
authorAlan Modra <amodra@gmail.com>
Tue, 17 Nov 2020 02:11:36 +0000 (12:41 +1030)
committerAlan Modra <amodra@gmail.com>
Wed, 18 Nov 2020 13:16:39 +0000 (23:46 +1030)
* doc/as.texi (.nop): Document optional size arg.
* dwarf2dbg.c (dwarf2_gen_line_info_1): Only check SEC_ALLOC
when ELF.  Warn whenever dwarf line number information is ignored.
* frags.c (frag_offset_ignore_align_p): New function.
* frags.h (frag_offset_ignore_align_p): Declare.
* read.c (s_nop): Extend to support optional size arg.
* testsuite/gas/elf/dwarf2-20.d: Expect warnings, and exact range.
* testsuite/gas/elf/dwarf2-20.s: Emit 16 bytes worth of nops.
* testsuite/gas/m68hc11/indexed12.d: Expect warnings.

gas/ChangeLog
gas/doc/as.texi
gas/dwarf2dbg.c
gas/frags.c
gas/frags.h
gas/read.c
gas/testsuite/gas/elf/dwarf2-20.d
gas/testsuite/gas/elf/dwarf2-20.s
gas/testsuite/gas/m68hc11/indexed12.d

index fcfce70fc7cc9bdad9a7879b50b525cbeb5263a6..92665855507f8c5b7b5b8e04cf770807a68e395c 100644 (file)
@@ -1,3 +1,15 @@
+2020-11-18  Alan Modra  <amodra@gmail.com>
+
+       * doc/as.texi (.nop): Document optional size arg.
+       * dwarf2dbg.c (dwarf2_gen_line_info_1): Only check SEC_ALLOC
+       when ELF.  Warn whenever dwarf line number information is ignored.
+       * frags.c (frag_offset_ignore_align_p): New function.
+       * frags.h (frag_offset_ignore_align_p): Declare.
+       * read.c (s_nop): Extend to support optional size arg.
+       * testsuite/gas/elf/dwarf2-20.d: Expect warnings, and exact range.
+       * testsuite/gas/elf/dwarf2-20.s: Emit 16 bytes worth of nops.
+       * testsuite/gas/m68hc11/indexed12.d: Expect warnings.
+
 2020-11-18  Jozef Lawrynowicz  <jozef.l@mittosystems.com>
        H.J. Lu  <hongjiu.lu@intel.com>
 
index 84a7e6191a3bde35ceb9af646a180164239b95d5..983cec3cbf988becaf875a33f19a1813a5a3067d 100644 (file)
@@ -6169,14 +6169,18 @@ counter, and @code{.nolist} decrements it.  Assembly listings are
 generated whenever the counter is greater than zero.
 
 @node Nop
-@section @code{.nop}
+@section @code{.nop [@var{size}]}
 
 @cindex @code{nop} directive
 @cindex filling memory with no-op instructions
-This directive emits a single no-op instruction.  It is provided on all
-architectures, allowing the creation of architecture neutral tests involving
-actual code.  The size of the generated instruction is target specific.  The
-instruction does affect the generation of DWARF debug line information.
+This directive emits no-op instructions.  It is provided on all architectures,
+allowing the creation of architecture neutral tests involving actual code.  The
+size of the generated instruction is target specific, but if the optional
+@var{size} argument is given and resolves to an absolute positive value at that
+point in assembly (no forward expressions allowed) then the fewest no-op
+instructions are emitted that equal or exceed a total @var{size} in bytes.
+@code{.nop} does affect the generation of DWARF debug line information.
+Some targets do not support using @code{.nop} with @var{size}.
 
 @node Nops
 @section @code{.nops @var{size}[, @var{control}]}
index 25ebc94a8d2b4c51279290770f188bf0ae60be19..e927c5059b8af36cecb30cea37214e915f72c4cc 100644 (file)
@@ -504,16 +504,18 @@ dwarf2_gen_line_info_1 (symbolS *label, struct dwarf2_line_info *loc)
 {
   struct line_subseg *lss;
   struct line_entry *e;
-  flagword need_flags = SEC_ALLOC | SEC_LOAD | SEC_CODE;
+  flagword need_flags = SEC_LOAD | SEC_CODE;
 
-  /* PR 26850: Do not record LOCs in non-executable, non-allocated,
-     or non-loaded sections.  */
+  /* PR 26850: Do not record LOCs in non-executable or non-loaded
+     sections.  SEC_ALLOC isn't tested for non-ELF because obj-coff.c
+     obj_coff_section is careless in setting SEC_ALLOC.  */
+  if (IS_ELF)
+    need_flags |= SEC_ALLOC;
   if ((now_seg->flags & need_flags) != need_flags)
     {
-      if (! SEG_NORMAL (now_seg))
-       /* FIXME: Add code to suppress multiple warnings ?  */
-       as_warn ("dwarf line number information for %s ignored",
-                segment_name (now_seg));
+      /* FIXME: Add code to suppress multiple warnings ?  */
+      as_warn ("dwarf line number information for %s ignored",
+              segment_name (now_seg));
       return;
     }
 
index c926ec3ba1ea5a92ca9966306c889ee27d95ea80..9ed4d7bc0d127fa25a695523c3091ef97b211416 100644 (file)
@@ -468,6 +468,48 @@ frag_offset_fixed_p (const fragS *frag1, const fragS *frag2, offsetT *offset)
   return FALSE;
 }
 
+/* Return TRUE if FRAG2 follows FRAG1 with a fixed relationship
+   between the two assuming alignment frags do nothing.  Set OFFSET to
+   the difference in address not already accounted for in the frag
+   FR_ADDRESS.  */
+
+bfd_boolean
+frag_offset_ignore_align_p (const fragS *frag1, const fragS *frag2,
+                           offsetT *offset)
+{
+  const fragS *frag;
+  offsetT off;
+
+  /* Start with offset initialised to difference between the two frags.
+     Prior to assigning frag addresses this will be zero.  */
+  off = frag1->fr_address - frag2->fr_address;
+  if (frag1 == frag2)
+    {
+      *offset = off;
+      return TRUE;
+    }
+
+  frag = frag1;
+  while (frag->fr_type == rs_fill
+        || frag->fr_type == rs_align
+        || frag->fr_type == rs_align_code
+        || frag->fr_type == rs_align_test)
+    {
+      if (frag->fr_type == rs_fill)
+       off += frag->fr_fix + frag->fr_offset * frag->fr_var;
+      frag = frag->fr_next;
+      if (frag == NULL)
+       break;
+      if (frag == frag2)
+       {
+         *offset = off;
+         return TRUE;
+       }
+    }
+
+  return FALSE;
+}
+
 /* Return TRUE if we can determine whether FRAG2 OFF2 appears after
    (strict >, not >=) FRAG1 OFF1, assuming it is not before.  Set
    *OFFSET so that resolve_expression will resolve an O_gt operation
index 39005ae71bc93f8a4985641dbd82b018f78ea0c1..6e519ab783b23bd46e5657b2654fcadaf3e3be1e 100644 (file)
@@ -154,6 +154,8 @@ char *frag_var (relax_stateT type,
                char *opcode);
 
 bfd_boolean frag_offset_fixed_p (const fragS *, const fragS *, offsetT *);
+bfd_boolean frag_offset_ignore_align_p (const fragS *, const fragS *,
+                                       offsetT *);
 bfd_boolean frag_gtoffset_p (valueT, const fragS *, valueT, const fragS *,
                             offsetT *);
 
index 9ba61cd96f4473f413ca80a5e876e38f525f5fcf..a4c6e4ed83a9f33fbd09340b2bd02014de2898b9 100644 (file)
@@ -3506,6 +3506,11 @@ s_space (int mult)
 void
 s_nop (int ignore ATTRIBUTE_UNUSED)
 {
+  expressionS exp;
+  fragS *start;
+  addressT start_off;
+  offsetT frag_off;
+
 #ifdef md_flush_pending_output
   md_flush_pending_output ();
 #endif
@@ -3515,29 +3520,42 @@ s_nop (int ignore ATTRIBUTE_UNUSED)
 #endif
 
   SKIP_WHITESPACE ();
+  expression (&exp);
   demand_empty_rest_of_line ();
 
+  start = frag_now;
+  start_off = frag_now_fix ();
+  do
+    {
 #ifdef md_emit_single_noop
-  md_emit_single_noop;
+      md_emit_single_noop;
 #else
-  char * nop;
+      char *nop;
 
 #ifndef md_single_noop_insn
 #define md_single_noop_insn "nop"
 #endif
-  /* md_assemble might modify its argument, so
-     we must pass it a string that is writeable.  */
-  if (asprintf (&nop, "%s", md_single_noop_insn) < 0)
-    as_fatal ("%s", xstrerror (errno));
-
-  /* Some targets assume that they can update input_line_pointer inside
-     md_assemble, and, worse, that they can leave it assigned to the string
-     pointer that was provided as an argument.  So preserve ilp here.  */
-  char * saved_ilp = input_line_pointer;
-  md_assemble (nop);
-  input_line_pointer = saved_ilp;
-  free (nop);
+      /* md_assemble might modify its argument, so
+        we must pass it a string that is writable.  */
+      if (asprintf (&nop, "%s", md_single_noop_insn) < 0)
+       as_fatal ("%s", xstrerror (errno));
+
+      /* Some targets assume that they can update input_line_pointer
+        inside md_assemble, and, worse, that they can leave it
+        assigned to the string pointer that was provided as an
+        argument.  So preserve ilp here.  */
+      char *saved_ilp = input_line_pointer;
+      md_assemble (nop);
+      input_line_pointer = saved_ilp;
+      free (nop);
+#endif
+#ifdef md_flush_pending_output
+      md_flush_pending_output ();
 #endif
+    } while (exp.X_op == O_constant
+            && exp.X_add_number > 0
+            && frag_offset_ignore_align_p (start, frag_now, &frag_off)
+            && frag_off + frag_now_fix () < start_off + exp.X_add_number);
 }
 
 void
index 363510a9b091a4760b650fada40326e53f456d0e..7f3d21cec995e797e9cb8f7d8e69f7cbe9176f6b 100644 (file)
@@ -3,6 +3,12 @@
 #name: DWARF2_20: debug ranges ignore non-code sections
 # The mn10200 target has a pointer size of 3, but it does not use segment selectors.  This confuses DWARF and readelf will complain.
 #xfail: mn102*-*
+# score-elf, tic6x-elf and xtensa-elf need special handling to support .nop 16
+#xfail: score-* tic6x-* xtensa-*
+#warning: .* \.alloc0 ignored
+#warning: .* \.alloc1 ignored
+#warning: .* \.nonalloc ignored
+#warning: .* \.nonallocexec ignored
 
 Contents of the .debug_aranges section:
 
@@ -13,6 +19,6 @@ Contents of the .debug_aranges section:
 [      ]+Segment Size:[        ]+0
 
 [      ]+Address[      ]+Length
-[      ]+0+000 0+00. 
+[      ]+0+000 0+010 
 [      ]+0+000 0+000 
 #pass
index 0ad0cc3ff029b81f52206e2400d1f144830a4c92..00b631448be1d0acc8e4b01105671c272830cc39 100644 (file)
@@ -1,10 +1,10 @@
        .section .alloc0,"a"
-       .nop
+       .nop 16
        .section .alloc1,"a"
-       .nop
+       .nop 16
        .section .nonalloc,""
-       .nop
+       .nop 16
        .section .allocexec,"ax"
-       .nop
+       .nop 16
        .section .nonallocexec,"x"
-       .nop
+       .nop 16
index 1862b6ac0742f9dcfeee16d0ea01bff0913b25f7..08279d73941234b6f6a9091a0113c3578a245d15 100644 (file)
@@ -2,6 +2,10 @@
 #as: -m68hc12 -gdwarf2
 #name: 68HC12 indexed addressing mode with 5, 9 and 16-bit offsets (indexed12)
 #source: indexed12.s
+#warning: .* line number information for \.data ignored
+#warning: .* line number information for \.data ignored
+#warning: .* line number information for \.data ignored
+#warning: .* line number information for \.data ignored
 
 .*: +file format elf32\-m68hc12