2010-09-15 Kai Tietz <kai.tietz@onevision.com>
- * config/obj-coff-seh.h (seh_context): New member code_seg.
- * config/obj-coff-seh.c: Implementing xdata/pdata section cloning
- for link-once code-segment.
+ * config/obj-coff-seh.c (seh_validate_seg): New funtion.
+ (obj_coff_seh_endproc): Add check for segment.
+ (obj_coff_seh_endprologue): Likewise.
+ (obj_coff_seh_pushreg): Likewise.
+ (obj_coff_seh_pushframe): Likewise.
+ (obj_coff_seh_save): Likewise.
+ (obj_coff_seh_setframe): Likewise.
+
+ * config/obj-coff-seh.h (seh_context): New member code_seg.
+ * config/obj-coff-seh.c: Implementing xdata/pdata section cloning
+ for link-once code-segment.
2010-09-14 Jie Zhang <jie@codesourcery.com>
return item;
}
+/* Check if current segment has same name. */
+static int
+seh_validate_seg (const char *directive)
+{
+ const char *cseg_name, *nseg_name;
+ if (seh_ctx_cur->code_seg == now_seg)
+ return 1;
+ cseg_name = bfd_get_section_name (stdoutput, seh_ctx_cur->code_seg);
+ nseg_name = bfd_get_section_name (stdoutput, now_seg);
+ as_bad (_("%s used in segment '%s' instead of expected '%s'"),
+ directive, nseg_name, cseg_name);
+ ignore_rest_of_line ();
+ return 0;
+}
+
static void
switch_xdata (int subseg, segT code_seg)
{
as_bad (_(".seh_endproc used without .seh_proc"));
return;
}
-
+ seh_validate_seg (".seh_endproc");
do_seh_endproc ();
}
static void
obj_coff_seh_endprologue (int what ATTRIBUTE_UNUSED)
{
- if (!verify_context (".seh_endprologue"))
+ if (!verify_context (".seh_endprologue")
+ || !seh_validate_seg (".seh_endprologue"))
return;
demand_empty_rest_of_line ();
{
int reg;
- if (!verify_context_and_target (".seh_pushreg", seh_kind_x64))
+ if (!verify_context_and_target (".seh_pushreg", seh_kind_x64)
+ || !seh_validate_seg (".seh_pushreg"))
return;
reg = seh_x64_read_reg (".seh_pushreg", 1);
static void
obj_coff_seh_pushframe (int what ATTRIBUTE_UNUSED)
{
- if (!verify_context_and_target (".seh_pushframe", seh_kind_x64))
+ if (!verify_context_and_target (".seh_pushframe", seh_kind_x64)
+ || !seh_validate_seg (".seh_pushframe"))
return;
demand_empty_rest_of_line ();
int code, reg, scale;
offsetT off;
- if (!verify_context_and_target (directive, seh_kind_x64))
+ if (!verify_context_and_target (directive, seh_kind_x64)
+ || !seh_validate_seg (directive))
return;
reg = seh_x64_read_reg (directive, what);
offsetT off;
int code, info;
- if (!verify_context_and_target (".seh_stackalloc", seh_kind_x64))
+ if (!verify_context_and_target (".seh_stackalloc", seh_kind_x64)
+ || !seh_validate_seg (".seh_stackalloc"))
return;
off = get_absolute_expression ();
offsetT off;
int reg;
- if (!verify_context_and_target (".seh_setframe", seh_kind_x64))
+ if (!verify_context_and_target (".seh_setframe", seh_kind_x64)
+ || !seh_validate_seg (".seh_setframe"))
return;
reg = seh_x64_read_reg (".seh_setframe", 0);
2010-09-15 Kai Tietz <kai.tietz@onevision.com>
- * gas/pe/pe.exp: Add peseh-x64-4,5,6 tests.
- * gas/pe/peseh-x64-4.s: New.
- * gas/pe/peseh-x64-4.d: New.
- * gas/pe/peseh-x64-5.d: New.
- * gas/pe/peseh-x64-6.d: New.
+ * gas/pe/pe.exp: Add new test.
+ * gas/pe/seh-x64-err-1.l: New.
+ * gas/pe/seh-x64-err-1.s: New.
+
+ * gas/pe/pe.exp: Add peseh-x64-4,5,6 tests.
+ * gas/pe/peseh-x64-4.s: New.
+ * gas/pe/peseh-x64-4.d: New.
+ * gas/pe/peseh-x64-5.d: New.
+ * gas/pe/peseh-x64-6.d: New.
2010-09-14 Maciej W. Rozycki <macro@codesourcery.com>
# These tests are only for x86_64 targets
if ([istarget "x86_64-*-mingw*"]) then {
-
+ run_list_test "seh-x64-err-1" ""
run_dump_test "peseh-x64"
run_dump_test "peseh-x64-2"
run_dump_test "peseh-x64-3"
--- /dev/null
+.*: Assembler messages:
+.*:5: Error: .seh_endproc used without .seh_proc
+.*:6: Error: .seh_stackalloc used outside of .seh_proc block
+.*:7: Error: .seh_setframe used outside of .seh_proc block
+.*:8: Error: .seh_endprologue used outside of .seh_proc block
+.*:9: Error: .seh_pushreg used outside of .seh_proc block
+.*:10: Error: .seh_savereg used outside of .seh_proc block
+.*:11: Error: .seh_savexmm used outside of .seh_proc block
+.*:12: Error: .seh_handler used outside of .seh_proc block
+.*:13: Error: .seh_handler used outside of .seh_proc block
+.*:14: Error: .seh_handler used outside of .seh_proc block
+.*:15: Error: .seh_handler used outside of .seh_proc block
+.*:16: Error: .seh_handlerdata used outside of .seh_proc block
+.*:19: Error: .seh_proc requires function label name
+.*:23: Warning: .seh_eh ignored for this target
+.*:24: Warning: .seh_32 ignored for this target
+.*:25: Warning: .seh_no32 ignored for this target
+.*:33: Error: .seh_stackalloc used in segment '.data' instead of expected '.text'
+.*:34: Error: .seh_setframe used in segment '.data' instead of expected '.text'
+.*:35: Error: .seh_endprologue used in segment '.data' instead of expected '.text'
+.*:36: Error: .seh_pushreg used in segment '.data' instead of expected '.text'
+.*:37: Error: .seh_savereg used in segment '.data' instead of expected '.text'
+.*:38: Error: .seh_savexmm used in segment '.data' instead of expected '.text'
+.*:39: Error: .seh_endproc used in segment '.data' instead of expected '.text'
--- /dev/null
+ .file "t1.c"
+ .text
+#seh pseudos out of seh_proc block
+
+ .seh_endproc
+ .seh_stackalloc 8
+ .seh_setframe %rbp, 0
+ .seh_endprologue
+ .seh_pushreg %rbp
+ .seh_savereg %rbp
+ .seh_savexmm %xmm1
+ .seh_handler dummy_handler
+ .seh_handler dummy_handler, @unwind
+ .seh_handler dummy_handler, @except
+ .seh_handler dummy_handler, @unwind,@except
+ .seh_handlerdata
+ .long 0
+ .text
+ .seh_proc
+
+ .seh_proc test_foreign_directives
+test_foreign_directives:
+ .seh_eh
+ .seh_32
+ .seh_no32
+ .long 0
+ .seh_endproc
+
+# test for wrong segment pseudos.
+ .seh_proc test_wrong_segment
+test_wrong_segment:
+ .data
+ .seh_stackalloc 8
+ .seh_setframe %rbp, 0
+ .seh_endprologue
+ .seh_pushreg %rbp
+ .seh_savereg %rbp
+ .seh_savexmm %xmm1
+ .seh_endproc
+