[PATCH 6/6] x86: handle SVR4 escaped binary operators

Jan Beulich jbeulich@suse.com
Fri Jul 17 13:53:45 GMT 2020


PR gas/4572

When / is a comment character, its use as binary "divide" operator needs
escaping by a backslash. Besides the scrubber needing to support this
(addressed in an earlier change), there are also a few provisions needed
in target specific operator handling.

As the spec calls for % and * to also be escaped because of being
"overloaded", also recognize these, despite the overloading there not
really preventing their use as operators in most (%) or all (*) cases,
given the way how the rest of the assembler works.

To bring source and testsuite in line, also drop the TE_I386AIX part of
the respective conditional, as i?86-*-aix* support had been removed a
while ago.

gas/
2020-07-XX  Jan Beulich  <jbeulich@suse.com>

	PR gas/4572
	* config/tc-i386.c (i386_comment_chars): Drop TE_I386AIX from
	conditional around it.
	(md_begin): Insert backslash into operand_chars[] when slash is
	a comment character.
	* config/tc-i386-intel.c (i386_operator): Recognize \/, \%, and
	\* as operators when / may be a comment character.
	* testsuite/gas/i386/svr4.s, testsuite/gas/i386/svr4.d: New.
	* testsuite/gas/i386/i386.exp: Run new test.

---
How the interaction with Intel syntax handling would best be from an
abstract perspective isn't very clear; since general lexing and syntax
recognition aren't along the lines of true Intel syntax assemblers like
MASM, allowing the escaping even there seems most consistent with the
overall current situation to me.

--- a/gas/config/tc-i386-intel.c
+++ b/gas/config/tc-i386-intel.c
@@ -123,6 +123,16 @@ operatorT i386_operator (const char *nam
 {
   unsigned int j;
 
+#ifdef SVR4_COMMENT_CHARS
+  if (!name && operands == 2 && *input_line_pointer == '\\')
+    switch (input_line_pointer[1])
+      {
+      case '/': input_line_pointer += 2; return O_divide;
+      case '%': input_line_pointer += 2; return O_modulus;
+      case '*': input_line_pointer += 2; return O_multiply;
+      }
+#endif
+
   if (!intel_syntax)
     return O_absent;
 
--- a/gas/config/tc-i386.c
+++ b/gas/config/tc-i386.c
@@ -480,13 +480,12 @@ const char extra_symbol_chars[] = "*%-([
 #endif
 	;
 
-#if (defined (TE_I386AIX)				\
-     || ((defined (OBJ_ELF) || defined (OBJ_MAYBE_ELF))	\
-	 && !defined (TE_GNU)				\
-	 && !defined (TE_LINUX)				\
-	 && !defined (TE_FreeBSD)			\
-	 && !defined (TE_DragonFly)			\
-	 && !defined (TE_NetBSD)))
+#if ((defined (OBJ_ELF) || defined (OBJ_MAYBE_ELF))	\
+     && !defined (TE_GNU)				\
+     && !defined (TE_LINUX)				\
+     && !defined (TE_FreeBSD)				\
+     && !defined (TE_DragonFly)				\
+     && !defined (TE_NetBSD))
 /* This array holds the chars that always start a comment.  If the
    pre-processor is disabled, these aren't very useful.  The option
    --divide will remove '/' from this list.  */
@@ -3116,6 +3115,10 @@ md_begin (void)
 	    mnemonic_chars[c] = c;
 	    operand_chars[c] = c;
 	  }
+#ifdef SVR4_COMMENT_CHARS
+	else if (c == '\\' && strchr (i386_comment_chars, '/'))
+	  operand_chars[c] = c;
+#endif
 
 	if (ISALPHA (c) || ISDIGIT (c))
 	  identifier_chars[c] = c;
--- a/gas/testsuite/gas/i386/i386.exp
+++ b/gas/testsuite/gas/i386/i386.exp
@@ -692,6 +692,14 @@ if [expr [istarget "i*86-*-*"] || [istar
 	run_dump_test "dw2-compressed-1"
 	run_dump_test "dw2-compressed-3a"
 	run_dump_test "dw2-compressed-3b"
+
+	if {![istarget "*-*-dragonfly*"]
+	    && ![istarget "*-*-gnu*"]
+	    && ![istarget "*-*-freebsd*"]
+	    && ![istarget "*-*-linux*"]
+	    && ![istarget "*-*-netbsd*"]} then {
+	    run_dump_test "svr4"
+	}
     }
 }
 
--- /dev/null
+++ b/gas/testsuite/gas/i386/svr4.d
@@ -0,0 +1,24 @@
+#objdump: -dtw
+#name: SVR4 comment char escape handling
+
+.*: +file format .*
+
+SYMBOL TABLE:
+0+00 .* \.text[ 	]+0+ \.text
+0+00 .* \.data[ 	]+0+ \.data
+0+00 .* \.bss[ 	]+0+ \.bss
+0+00 .* \.text[ 	]+0+ svr4
+0+04 .* \*ABS\*[ 	]+0+ a
+0+03 .* \*ABS\*[ 	]+0+ b
+0+4c .* \*ABS\*[ 	]+0+ c
+
+Disassembly of section .text:
+
+0+0 <svr4>:
+[	 ]*[0-9a-f]+:[	 ]+b0 07[	 ]+mov    \$0x7,%al
+[	 ]*[0-9a-f]+:[	 ]+b0 01[	 ]+mov    \$0x1,%al
+[	 ]*[0-9a-f]+:[	 ]+b0 1e[	 ]+mov    \$0x1e,%al
+[	 ]*[0-9a-f]+:[	 ]+b0 05[	 ]+mov    \$0x5,%al
+[	 ]*[0-9a-f]+:[	 ]+b0 02[	 ]+mov    \$0x2,%al
+[	 ]*[0-9a-f]+:[	 ]+b0 33[	 ]+mov    \$0x33,%al
+#pass
--- /dev/null
+++ b/gas/testsuite/gas/i386/svr4.s
@@ -0,0 +1,31 @@
+	.text
+
+	.if 1 / 2
+	.else
+	.error
+	.endif
+
+	.if 1 \/ 2
+	.error
+	.endif
+
+	.if 4 \% 2
+	.error
+	.endif
+
+	.if 1 \* 0
+	.error
+	.endif
+
+svr4:
+	mov	$(15 \/ 2), %al
+	mov	$(15 \% 2), %al
+	mov	$(15 \* 2), %al
+
+	.byte	0xb0, 17 \/ 3
+	.byte	0xb0, 17 \% 3
+	.byte	0xb0, 17 \* 3
+
+	.equiv	a, 19 \/ 4
+	.equiv	b, 19 \% 4
+	.equiv	c, 19 \* 4



More information about the Binutils mailing list