gas x86-32: allow non-absolute segment values for lcall/ljmp?
TK Chia
u1049321969@caramail.com
Sun Oct 4 16:20:00 GMT 2020
Hello all,
>>>> $ gas/as-new --32 test5.s
>>>> test5.s: Assembler messages:
>>>> test5.s:2: Error: can't handle non absolute segment in `lcall'
>>>> ======================================================================
Enclosed please find my updated proposed patch to remove this
restriction. I have also submitted the patch on Bugzilla
(https://sourceware.org/bugzilla/show_bug.cgi?id=26694).
gas changes:
2020-10-04 T.K. Chia <u1049321969@caramail.com>
PR 26694
* config/tc-i386.c (output_interseg_jump): Allow non-absolute
segment operand for immediate lcall/ljmp.
* testsuite/gas/i386/jump.d,
* testsuite/gas/i386/jump.s,
* testsuite/gas/i386/jump16.d,
* testsuite/gas/i386/jump16.e,
* testsuite/gas/i386/jump16.s: Add tests for non-absolute
segment operand for immediate ljmp.
ld changes:
2020-10-04 T.K. Chia <u1049321969@caramail.com>
PR gas/26694
* testsuite/ld-i386/ljmp.s,
* testsuite/ld-i386/ljmp1.d,
* testsuite/ld-i386/ljmp1.s,
* testsuite/ld-i386/ljmp2.d,
* testsuite/ld-i386/ljmp2.s,
* testsuite/ld-x86-64/ljmp1.d,
* testsuite/ld-x86-64/ljmp2.d: New testcases.
* testsuite/ld-i386/i386.exp,
* testsuite/ld-x86-64/x86-64.exp: Run them.
Thank you very much!
--
https://github.com/tkchia
-------------- next part --------------
diff --git a/gas/ChangeLog b/gas/ChangeLog
index 60a952bd92..25d728bb3c 100644
--- a/gas/ChangeLog
+++ b/gas/ChangeLog
@@ -1,3 +1,15 @@
+2020-10-04 T.K. Chia <u1049321969@caramail.com>
+
+ PR 26694
+ * config/tc-i386.c (output_interseg_jump): Allow non-absolute
+ segment operand for immediate lcall/ljmp.
+ * testsuite/gas/i386/jump.d,
+ * testsuite/gas/i386/jump.s,
+ * testsuite/gas/i386/jump16.d,
+ * testsuite/gas/i386/jump16.e,
+ * testsuite/gas/i386/jump16.s: Add tests for non-absolute
+ segment operand for immediate ljmp.
+
2020-09-30 Alex Coplan <alex.coplan@arm.com>
* NEWS: Mention recent Arm processor support.
diff --git a/gas/config/tc-i386.c b/gas/config/tc-i386.c
index 4891c45a1a..d0f66c96dc 100644
--- a/gas/config/tc-i386.c
+++ b/gas/config/tc-i386.c
@@ -8759,10 +8759,13 @@ output_interseg_jump (void)
else
fix_new_exp (frag_now, p - frag_now->fr_literal, size,
i.op[1].imms, 0, reloc (size, 0, 0, i.reloc[1]));
- if (i.op[0].imms->X_op != O_constant)
- as_bad (_("can't handle non absolute segment in `%s'"),
- i.tm.name);
- md_number_to_chars (p + size, (valueT) i.op[0].imms->X_add_number, 2);
+
+ p += size;
+ if (i.op[0].imms->X_op == O_constant)
+ md_number_to_chars (p, (valueT) i.op[0].imms->X_add_number, 2);
+ else
+ fix_new_exp (frag_now, p - frag_now->fr_literal, 2,
+ i.op[0].imms, 0, reloc (2, 0, 0, i.reloc[0]));
}
#if defined (OBJ_ELF) || defined (OBJ_MAYBE_ELF)
diff --git a/gas/testsuite/gas/i386/jump.d b/gas/testsuite/gas/i386/jump.d
index 6dcececc1f..72e399599c 100644
--- a/gas/testsuite/gas/i386/jump.d
+++ b/gas/testsuite/gas/i386/jump.d
@@ -54,4 +54,16 @@ Disassembly of section .text:
[ ]*[a-f0-9]+: ea 90 90 90 90 90 90 ljmp \$0x9090,\$0x90909090
[ ]*[a-f0-9]+: ea 00 00 00 00 90 90 ljmp \$0x9090,\$0x0[ ]+[a-f0-9]+: (R_386_)?(dir)?32 xxx
[ ]*[a-f0-9]+: ea 00 00 00 00 90 90 ljmp \$0x9090,\$0x0[ ]+[a-f0-9]+: (R_386_)?(dir)?32 xxx
+[ ]*[a-f0-9]+: ea 90 90 90 90 00 00 ljmp \$0x0,\$0x90909090[ ]+[a-f0-9]+: (R_386_)?(dir)?16 yyy
+[ ]*[a-f0-9]+: ea 90 90 90 90 00 00 ljmp \$0x0,\$0x90909090[ ]+[a-f0-9]+: (R_386_)?(dir)?16 yyy
+[ ]*[a-f0-9]+: ea 00 00 00 00 00 00 ljmp \$0x0,\$0x0[ ]+[a-f0-9]+: (R_386_)?(dir)?32 xxx
+[ ]+[a-f0-9]+: (R_386_)?(dir)?16 yyy
+[ ]*[a-f0-9]+: ea 00 00 00 00 00 00 ljmp \$0x0,\$0x0[ ]+[a-f0-9]+: (R_386_)?(dir)?32 xxx
+[ ]+[a-f0-9]+: (R_386_)?(dir)?16 yyy
+[ ]*[a-f0-9]+: ea 90 90 90 90 00 00 ljmp \$0x0,\$0x90909090[ ]+[a-f0-9]+: (R_386_)?(dir)?16 yyy
+[ ]*[a-f0-9]+: ea 90 90 90 90 00 00 ljmp \$0x0,\$0x90909090[ ]+[a-f0-9]+: (R_386_)?(dir)?16 yyy
+[ ]*[a-f0-9]+: ea 00 00 00 00 00 00 ljmp \$0x0,\$0x0[ ]+[a-f0-9]+: (R_386_)?(dir)?32 xxx
+[ ]+[a-f0-9]+: (R_386_)?(dir)?16 yyy
+[ ]*[a-f0-9]+: ea 00 00 00 00 00 00 ljmp \$0x0,\$0x0[ ]+[a-f0-9]+: (R_386_)?(dir)?32 xxx
+[ ]+[a-f0-9]+: (R_386_)?(dir)?16 yyy
#pass
diff --git a/gas/testsuite/gas/i386/jump.s b/gas/testsuite/gas/i386/jump.s
index eec3f0ab63..5efe43882a 100644
--- a/gas/testsuite/gas/i386/jump.s
+++ b/gas/testsuite/gas/i386/jump.s
@@ -1,6 +1,7 @@
.psize 0
.text
.extern xxx
+.extern yyy
1: jmp 1b
jmp xxx
@@ -54,3 +55,11 @@
jmp 0x9090:0x90909090
jmp 0x9090,xxx
jmp 0x9090:xxx
+ ljmp yyy,0x90909090
+ ljmp yyy:0x90909090
+ ljmp yyy,xxx
+ ljmp yyy:xxx
+ jmp yyy,0x90909090
+ jmp yyy:0x90909090
+ jmp yyy,xxx
+ jmp yyy:xxx
diff --git a/gas/testsuite/gas/i386/jump16.d b/gas/testsuite/gas/i386/jump16.d
index afb1c377e7..df4facc10c 100644
--- a/gas/testsuite/gas/i386/jump16.d
+++ b/gas/testsuite/gas/i386/jump16.d
@@ -68,6 +68,18 @@ Disassembly of section .text:
[ ]*[a-f0-9]+: ea 10 10 90 90 ljmp \$0x9090,\$0x1010
[ ]*[a-f0-9]+: ea 00 00 90 90 ljmp \$0x9090,\$0x0 ed: (R_386_)?16 xxx
[ ]*[a-f0-9]+: ea 00 00 90 90 ljmp \$0x9090,\$0x0 f2: (R_386_)?16 xxx
+[ ]*[a-f0-9]+: ea 10 10 00 00 ljmp \$0x0,\$0x1010 f9: (R_386_)?16 yyy
+[ ]*[a-f0-9]+: ea 10 10 00 00 ljmp \$0x0,\$0x1010 fe: (R_386_)?16 yyy
+[ ]*[a-f0-9]+: ea 00 00 00 00 ljmp \$0x0,\$0x0 101: (R_386_)?16 xxx
+[ ]+103: (R_386_)?16 yyy
+[ ]*[a-f0-9]+: ea 00 00 00 00 ljmp \$0x0,\$0x0 106: (R_386_)?16 xxx
+[ ]+108: (R_386_)?16 yyy
+[ ]*[a-f0-9]+: ea 10 10 00 00 ljmp \$0x0,\$0x1010 10d: (R_386_)?16 yyy
+[ ]*[a-f0-9]+: ea 10 10 00 00 ljmp \$0x0,\$0x1010 112: (R_386_)?16 yyy
+[ ]*[a-f0-9]+: ea 00 00 00 00 ljmp \$0x0,\$0x0 115: (R_386_)?16 xxx
+[ ]+117: (R_386_)?16 yyy
+[ ]*[a-f0-9]+: ea 00 00 00 00 ljmp \$0x0,\$0x0 11a: (R_386_)?16 xxx
+[ ]+11c: (R_386_)?16 yyy
[ ]*[a-f0-9]+: cf iret
[ ]*[a-f0-9]+: cf iret
[ ]*[a-f0-9]+: 66 cf iretl
diff --git a/gas/testsuite/gas/i386/jump16.e b/gas/testsuite/gas/i386/jump16.e
index 2ad7ea056b..aa5c5aad65 100644
--- a/gas/testsuite/gas/i386/jump16.e
+++ b/gas/testsuite/gas/i386/jump16.e
@@ -1,3 +1,3 @@
.*: Assembler messages:
-.*:77: Warning: generating 16-bit `iret' for .code16gcc directive
-.*:88: Warning: generating 16-bit `iret' for .code16gcc directive
+.*:86: Warning: generating 16-bit `iret' for .code16gcc directive
+.*:97: Warning: generating 16-bit `iret' for .code16gcc directive
diff --git a/gas/testsuite/gas/i386/jump16.s b/gas/testsuite/gas/i386/jump16.s
index fb9e830c52..42d150ff97 100644
--- a/gas/testsuite/gas/i386/jump16.s
+++ b/gas/testsuite/gas/i386/jump16.s
@@ -1,6 +1,7 @@
.psize 0
.text
.extern xxx
+.extern yyy
.code16gcc
1: jmp 1b
@@ -71,6 +72,14 @@
jmp 0x9090:0x1010
jmp 0x9090,xxx
jmp 0x9090:xxx
+ ljmp yyy,0x1010
+ ljmp yyy:0x1010
+ ljmp yyy,xxx
+ ljmp yyy:xxx
+ jmp yyy,0x1010
+ jmp yyy:0x1010
+ jmp yyy,xxx
+ jmp yyy:xxx
.att_syntax
.code16gcc
diff --git a/ld/ChangeLog b/ld/ChangeLog
index 369252761c..f26d282565 100644
--- a/ld/ChangeLog
+++ b/ld/ChangeLog
@@ -1,3 +1,16 @@
+2020-10-04 T.K. Chia <u1049321969@caramail.com>
+
+ PR gas/26694
+ * testsuite/ld-i386/ljmp.s,
+ * testsuite/ld-i386/ljmp1.d,
+ * testsuite/ld-i386/ljmp1.s,
+ * testsuite/ld-i386/ljmp2.d,
+ * testsuite/ld-i386/ljmp2.s,
+ * testsuite/ld-x86-64/ljmp1.d,
+ * testsuite/ld-x86-64/ljmp2.d: New testcases.
+ * testsuite/ld-i386/i386.exp,
+ * testsuite/ld-x86-64/x86-64.exp: Run them.
+
2020-09-30 Jeremy Drake <sourceware-bugzilla@jdrake.com>
PR 26588
diff --git a/ld/testsuite/ld-i386/i386.exp b/ld/testsuite/ld-i386/i386.exp
index 164c099cbb..d0b8ed77bd 100644
--- a/ld/testsuite/ld-i386/i386.exp
+++ b/ld/testsuite/ld-i386/i386.exp
@@ -342,6 +342,8 @@ run_dump_test "call3g"
run_dump_test "call3h"
run_dump_test "jmp1"
run_dump_test "jmp2"
+run_dump_test "ljmp1"
+run_dump_test "ljmp2"
run_dump_test "load1"
run_dump_test "load2"
run_dump_test "load3"
diff --git a/ld/testsuite/ld-i386/ljmp.s b/ld/testsuite/ld-i386/ljmp.s
new file mode 100644
index 0000000000..4b27a25a18
--- /dev/null
+++ b/ld/testsuite/ld-i386/ljmp.s
@@ -0,0 +1,10 @@
+ .global seg1
+ .equiv seg1, 8
+ .global seg2
+ .equiv seg2, 0x18
+ /* Bad IA-16 segment values --- will overflow R_386_16 (and
+ R_X86_64_16). */
+ .global seg3
+ .equiv seg3, 0x10000
+ .global seg4
+ .equiv seg4, -0x10001
diff --git a/ld/testsuite/ld-i386/ljmp1.d b/ld/testsuite/ld-i386/ljmp1.d
new file mode 100644
index 0000000000..9708ad0e00
--- /dev/null
+++ b/ld/testsuite/ld-i386/ljmp1.d
@@ -0,0 +1,18 @@
+#name: Absolute non-overflowing relocs in ljmp segments
+#as: --32
+#source: ljmp1.s
+#source: ljmp.s
+#ld: -melf_i386 -z noseparate-code
+#objdump: -dw
+
+.*: +file format .*
+
+
+Disassembly of section .text:
+
+0+[a-f0-9]+ <_start>:
+ +[a-f0-9]+: 0f 22 c0 mov %eax,%cr0
+ +[a-f0-9]+: ea ([0-9a-f]{2} ){4}08 00 ljmp \$0x8,\$0x[a-f0-9]+
+
+0+[a-f0-9]+ <foo>:
+ +[a-f0-9]+: 66 ea 00 00 18 00 ljmpw \$0x18,\$0x0
diff --git a/ld/testsuite/ld-i386/ljmp1.s b/ld/testsuite/ld-i386/ljmp1.s
new file mode 100644
index 0000000000..3ae6882de5
--- /dev/null
+++ b/ld/testsuite/ld-i386/ljmp1.s
@@ -0,0 +1,9 @@
+ .text
+.code32
+ .global _start
+_start:
+ movl %eax, %cr0
+ ljmp $seg1, $foo
+foo:
+ ljmpw $seg2, $0
+ .p2align 4,0x90
diff --git a/ld/testsuite/ld-i386/ljmp2.d b/ld/testsuite/ld-i386/ljmp2.d
new file mode 100644
index 0000000000..b599cf9868
--- /dev/null
+++ b/ld/testsuite/ld-i386/ljmp2.d
@@ -0,0 +1,7 @@
+#name: ljmp segment value overflow
+#as: --32
+#source: ljmp2.s
+#source: ljmp.s
+#ld: -melf_i386 -z noseparate-code
+#error: .*relocation truncated to fit: R_386_16 .*
+#error: .*relocation truncated to fit: R_386_16 .*
diff --git a/ld/testsuite/ld-i386/ljmp2.s b/ld/testsuite/ld-i386/ljmp2.s
new file mode 100644
index 0000000000..f6a4227a22
--- /dev/null
+++ b/ld/testsuite/ld-i386/ljmp2.s
@@ -0,0 +1,9 @@
+ .text
+.code32
+ .global _start
+_start:
+ movl %eax, %cr0
+ ljmp $seg3, $foo
+foo:
+ ljmpw $seg4, $0
+ .p2align 4,0x90
diff --git a/ld/testsuite/ld-x86-64/ljmp1.d b/ld/testsuite/ld-x86-64/ljmp1.d
new file mode 100644
index 0000000000..eb378fb607
--- /dev/null
+++ b/ld/testsuite/ld-x86-64/ljmp1.d
@@ -0,0 +1,17 @@
+#name: Absolute non-overflowing relocs in ljmp segments
+#source: ../ld-i386/ljmp1.s
+#source: ../ld-i386/ljmp.s
+#ld: -z noseparate-code
+#objdump: -Mi386 -dw
+
+.*: +file format .*
+
+
+Disassembly of section .text:
+
+0+[a-f0-9]+ <_start>:
+ +[a-f0-9]+: 0f 22 c0 mov %eax,%cr0
+ +[a-f0-9]+: ea ([0-9a-f]{2} ){4}08 00 ljmp \$0x8,\$0x[a-f0-9]+
+
+0+[a-f0-9]+ <foo>:
+ +[a-f0-9]+: 66 ea 00 00 18 00 ljmpw \$0x18,\$0x0
diff --git a/ld/testsuite/ld-x86-64/ljmp2.d b/ld/testsuite/ld-x86-64/ljmp2.d
new file mode 100644
index 0000000000..b3581822ce
--- /dev/null
+++ b/ld/testsuite/ld-x86-64/ljmp2.d
@@ -0,0 +1,6 @@
+#name: ljmp segment value overflow
+#source: ../ld-i386/ljmp2.s
+#source: ../ld-i386/ljmp.s
+#ld: -z noseparate-code
+#error: .*relocation truncated to fit: R_X86_64_16 .*
+#error: .*relocation truncated to fit: R_X86_64_16 .*
diff --git a/ld/testsuite/ld-x86-64/x86-64.exp b/ld/testsuite/ld-x86-64/x86-64.exp
index 3c0b4347d0..2c2551fd62 100644
--- a/ld/testsuite/ld-x86-64/x86-64.exp
+++ b/ld/testsuite/ld-x86-64/x86-64.exp
@@ -519,6 +519,8 @@ run_dump_test "mov2a"
run_dump_test "mov2b"
run_dump_test "mov2c"
run_dump_test "mov2d"
+run_dump_test "ljmp1"
+run_dump_test "ljmp2"
run_dump_test "load1a"
run_dump_test "load1b"
run_dump_test "load1c"
More information about the Binutils
mailing list