summaryrefslogtreecommitdiffstats
path: root/0021-__cxa-atexit-for-Cygwin.patch
blob: 58a58f853683e976640bb71292a4b0918874e475 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
From 4250ae25a96ddf8c48b978e1c4427d19c7279908 Mon Sep 17 00:00:00 2001
From: Jonathan Yong <10walls@gmail.com>
Date: Thu, 30 Oct 2014 17:15:02 +0800
Subject: [PATCH 21/24] __cxa-atexit for Cygwin

Using  __cxa_atexit(__gcc_deregister_frame, NULL, __dso_handle)
instead of atexit(__gcc_deregister_frame) directly to prevent an
optimization bug.
---
 gcc/config.gcc                        |  2 ++
 gcc/config/i386/cygwin.h              |  2 +-
 libgcc/config.host                    |  4 ++--
 libgcc/config/i386/cygming-crtbegin.c | 28 ++++++++++++++++++++++++++++
 libgcc/config/i386/cygming-crtend.c   |  6 ------
 libgcc/config/i386/t-cygming          |  3 +++
 6 files changed, 36 insertions(+), 9 deletions(-)

diff --git a/gcc/config.gcc b/gcc/config.gcc
index 90d4f71..2a432e6 100644
--- a/gcc/config.gcc
+++ b/gcc/config.gcc
@@ -1594,6 +1594,7 @@ i[34567]86-*-cygwin*)
 		thread_file='posix'
 	fi
 	use_gcc_stdint=wrap
+	default_use_cxa_atexit=yes
 	;;
 x86_64-*-cygwin*)
 	need_64bit_isa=yes
@@ -1902,6 +1903,7 @@ mep-*-*)
 		with_headers=yes
 	fi
 	use_gcc_stdint=wrap
+	default_use_cxa_atexit=yes
 	;;
 microblaze*-linux*)
 	case $target in
diff --git a/gcc/config/i386/cygwin.h b/gcc/config/i386/cygwin.h
index 4e15ab0..19e6b7e 100644
--- a/gcc/config/i386/cygwin.h
+++ b/gcc/config/i386/cygwin.h
@@ -40,7 +40,7 @@ along with GCC; see the file COPYING3.  If not see
 #define STARTFILE_SPEC "\
   %{!shared: %{!mdll: crt0%O%s \
   %{pg:gcrt0%O%s}}}\
-  crtbegin.o%s"
+  %{shared:crtbeginS.o%s;:crtbegin.o%s}"
 
 #undef ENDFILE_SPEC
 #define ENDFILE_SPEC \
diff --git a/libgcc/config.host b/libgcc/config.host
index f196680..08cac3f 100644
--- a/libgcc/config.host
+++ b/libgcc/config.host
@@ -603,7 +603,7 @@ i[34567]86-*-solaris2* | x86_64-*-solaris2.1[0-9]*)
 i[4567]86-wrs-vxworks|i[4567]86-wrs-vxworksae)
 	;;
 i[34567]86-*-cygwin*)
-	extra_parts="crtbegin.o crtend.o crtfastmath.o"
+	extra_parts="crtbegin.o crtbeginS.o crtend.o crtfastmath.o"
 	# This has to match the logic for DWARF2_UNWIND_INFO in gcc/config/i386/cygming.h
 	if test x$enable_sjlj_exceptions = xyes; then
 		tmake_eh_file="i386/t-sjlj-eh"
@@ -619,7 +619,7 @@ i[34567]86-*-cygwin*)
 	tmake_file="${tmake_file} ${tmake_eh_file} ${tmake_dlldir_file} i386/t-slibgcc-cygming i386/t-cygming i386/t-cygwin i386/t-crtfm i386/t-chkstk t-dfprules"
 	;;
 x86_64-*-cygwin*)
-	extra_parts="crtbegin.o crtend.o crtfastmath.o"
+	extra_parts="crtbegin.o crtbeginS.o crtend.o crtfastmath.o"
 	# This has to match the logic for DWARF2_UNWIND_INFO in gcc/config/i386/cygming.h
 	if test x$enable_sjlj_exceptions = xyes; then
 		tmake_eh_file="i386/t-sjlj-eh"
diff --git a/libgcc/config/i386/cygming-crtbegin.c b/libgcc/config/i386/cygming-crtbegin.c
index 195b463..aece23c 100644
--- a/libgcc/config/i386/cygming-crtbegin.c
+++ b/libgcc/config/i386/cygming-crtbegin.c
@@ -110,6 +110,23 @@ static void *__JCR_LIST__[]
   = { };
 #endif
 
+#ifdef __CYGWIN__
+/* Declare the __dso_handle variable.  It should have a unique value
+   in every shared-object; in a main program its value is zero.  The
+   object should in any case be protected.  This means the instance
+   in one DSO or the main program is not used in another object.  The
+   dynamic linker takes care of this.  */
+
+#ifdef CRTSTUFFS_O
+extern void *__ImageBase;
+void *__dso_handle = &__ImageBase;
+#else
+void *__dso_handle = 0;
+#endif
+
+#endif /* __CYGWIN__ */
+
+
 /* Pull in references from libgcc.a(unwind-dw2-fde.o) in the
    startfile. These are referenced by a ctor and dtor in crtend.o.  */
 extern void __gcc_register_frame (void);
@@ -155,6 +172,17 @@ __gcc_register_frame (void)
 	register_class_fn (__JCR_LIST__);
     }
 #endif
+
+#if DEFAULT_USE_CXA_ATEXIT
+  /* If we use the __cxa_atexit method to register C++ dtors
+     at object construction,  also use atexit to register eh frame
+     info cleanup.  */
+#ifdef __CYGWIN__
+  __cxa_atexit(__gcc_deregister_frame, NULL, (void *)&__dso_handle);
+#else
+  atexit(__gcc_deregister_frame);
+#endif /* __CYGWIN__ */
+#endif /* DEFAULT_USE_CXA_ATEXIT */
 }
 
 void
diff --git a/libgcc/config/i386/cygming-crtend.c b/libgcc/config/i386/cygming-crtend.c
index de0d61f..d3beaf9 100644
--- a/libgcc/config/i386/cygming-crtend.c
+++ b/libgcc/config/i386/cygming-crtend.c
@@ -70,12 +70,6 @@ static void
 register_frame_ctor (void)
 {
   __gcc_register_frame ();
-#if DEFAULT_USE_CXA_ATEXIT
-  /* If we use the __cxa_atexit method to register C++ dtors
-     at object construction,  also use atexit to register eh frame
-     info cleanup.  */
-  atexit (__gcc_deregister_frame);
-#endif
 }
 
 #if !DEFAULT_USE_CXA_ATEXIT
diff --git a/libgcc/config/i386/t-cygming b/libgcc/config/i386/t-cygming
index d76004c..4713b7f 100644
--- a/libgcc/config/i386/t-cygming
+++ b/libgcc/config/i386/t-cygming
@@ -8,6 +8,9 @@ CUSTOM_CRTSTUFF = yes
 crtbegin.o: $(srcdir)/config/i386/cygming-crtbegin.c
 	$(crt_compile) -fno-omit-frame-pointer  -c $<
 
+crtbeginS.o: $(srcdir)/config/i386/cygming-crtbegin.c
+	$(crt_compile) -fno-omit-frame-pointer  -c $< -DCRTSTUFFS_O
+
 # We intentionally use a implementation-reserved init priority of 0,
 # so allow the warning.
 crtend.o: $(srcdir)/config/i386/cygming-crtend.c
-- 
2.1.1