[binutils-gdb] x86: adjust segment override prefix emission
Jan Beulich
jbeulich@sourceware.org
Fri Feb 14 13:04:00 GMT 2020
https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=b6773884364e0275a793adad4b025913fa155d5a
commit b6773884364e0275a793adad4b025913fa155d5a
Author: Jan Beulich <jbeulich@suse.com>
Date: Fri Feb 14 14:04:23 2020 +0100
x86: adjust segment override prefix emission
Since we already suppress the prefix altogether when it's the default
one for the chosen addressing mode, let's do so also when instruction
prefix and override specified with the memory operand match. (Note that
insn prefix specified segment overrides never get discarded.)
Diff:
---
gas/ChangeLog | 8 ++++++++
gas/config/tc-i386.c | 12 +++++++-----
gas/testsuite/gas/i386/prefix32.l | 9 ++++++++-
gas/testsuite/gas/i386/prefix32.s | 6 ++++++
4 files changed, 29 insertions(+), 6 deletions(-)
diff --git a/gas/ChangeLog b/gas/ChangeLog
index 0cbd2a5..56d5071 100644
--- a/gas/ChangeLog
+++ b/gas/ChangeLog
@@ -1,5 +1,13 @@
2020-02-14 Jan Beulich <jbeulich@suse.com>
+ * config/tc-i386.c (process_operands): Also skip segment
+ override prefix emission if it matches an already present one.
+ * testsuite/gas/i386/prefix32.s: Add double segment override
+ cases.
+ * testsuite/gas/i386/prefix32.l: Adjust expectations.
+
+2020-02-14 Jan Beulich <jbeulich@suse.com>
+
* config/tc-i386.c (process_operands): Drop ineffectual segment
overrides when optimizing.
* testsuite/gas/i386/lea-optimize.d: New.
diff --git a/gas/config/tc-i386.c b/gas/config/tc-i386.c
index d7d45de..0e60919 100644
--- a/gas/config/tc-i386.c
+++ b/gas/config/tc-i386.c
@@ -7178,11 +7178,13 @@ duplicate:
}
/* If a segment was explicitly specified, and the specified segment
- is not the default, use an opcode prefix to select it. If we
- never figured out what the default segment is, then default_seg
- will be zero at this point, and the specified segment prefix will
- always be used. */
- if ((i.seg[0]) && (i.seg[0] != default_seg))
+ is neither the default nor the one already recorded from a prefix,
+ use an opcode prefix to select it. If we never figured out what
+ the default segment is, then default_seg will be zero at this
+ point, and the specified segment prefix will always be used. */
+ if (i.seg[0]
+ && i.seg[0] != default_seg
+ && i.seg[0]->seg_prefix != i.prefix[SEG_PREFIX])
{
if (!add_prefix (i.seg[0]->seg_prefix))
return 0;
diff --git a/gas/testsuite/gas/i386/prefix32.l b/gas/testsuite/gas/i386/prefix32.l
index 41c8d88..09a00cd 100644
--- a/gas/testsuite/gas/i386/prefix32.l
+++ b/gas/testsuite/gas/i386/prefix32.l
@@ -8,6 +8,7 @@
.*:19: Error: same type of prefix .*
.*:20: Error: data size .* `vaddps'
.*:21: Error: data size .* `vaddpd'
+.*:25: Error: same type of prefix .*
GAS LISTING .*
#...
[ ]*1[ ]+\.text
@@ -33,4 +34,10 @@ GAS LISTING .*
[ ]*20[ ]+data16 vaddps %xmm0, %xmm0, %xmm0
[ ]*21[ ]+data16 vaddpd %xmm0, %xmm0, %xmm0
[ ]*22[ ]*
-[ ]*23[ ]*[\?]+ 0+[ \t]+\.p2align 4,0
+[ ]*23[ ]+\.Lsegment:
+[ ]*24[ ]+\?\?\?\? 368B4500[ ]+ss mov %ss:\(%ebp\), %eax
+[ ]*25[ ]+ss mov %ds:\(%ebp\), %eax
+[ ]*26[ ]+\?\?\?\? 3E8B4500[ ]+ds mov %ss:\(%ebp\), %eax
+[ ]*27[ ]+\?\?\?\? 3E8B4500[ ]+ds mov %ds:\(%ebp\), %eax
+[ ]*28[ ]*
+#pass
diff --git a/gas/testsuite/gas/i386/prefix32.s b/gas/testsuite/gas/i386/prefix32.s
index 1ffdff1..a4382a2 100644
--- a/gas/testsuite/gas/i386/prefix32.s
+++ b/gas/testsuite/gas/i386/prefix32.s
@@ -20,4 +20,10 @@ prefix:
data16 vaddps %xmm0, %xmm0, %xmm0
data16 vaddpd %xmm0, %xmm0, %xmm0
+.Lsegment:
+ ss mov %ss:(%ebp), %eax
+ ss mov %ds:(%ebp), %eax
+ ds mov %ss:(%ebp), %eax
+ ds mov %ds:(%ebp), %eax
+
.p2align 4,0
More information about the Binutils-cvs
mailing list