Re: [Mingw-w64-public] [PATCH] crt: Unify and simplify handling of constructor/destructor lists

2018-08-27 Thread Martin Storsjö

On Mon, 27 Aug 2018, Liu Hao wrote:


This patch breaks libgcc.

At the moment the `__main()` function which performs global 
initialization for static objects cannot handle `__CTOR_LIST__` with two 
pointers of `-1` in the front of it [1]. The code is presumed to call 
every function via pointers between the first `-1` and final null 
terminator in reverse order, which, if the second element is a 
duplicated `-1`, will result in a segfault at the last iteration of the 
loop.


To clarify; mingw-w64-crt has got its own __main function, while libgcc 
provides another one. The one in mingw-w64 should handle this just fine, 
while the libgcc ones obviously doesn't.



Probably this patch should be reverted.


Yes, unless we come up with something better, soon. Feel free to revert, 
but please amend the commit message to clarify that there are two 
different implementations of the __main function; the one we have worked 
fine but the libgcc one didn't handle our special situation.


I had an idea to try to move the defintion of these symbols from 
crtexe.c/crtdll.c into gccmain.c, but that makes them turn up too late in 
the link, after constructors from some object files, so that doesn't 
really work.


If we revert this, my next alternative towards unifying this handling 
across binutils and lld, would be to first make mingw-w64 check for these 
symbols during the build so we can make the previous ifdefs a bit more 
flexible (not having to check for #ifdef __clang__, which the compiler 
doesn't say what linker one was going to use) - I have a pretty much ready 
patch for this already. Then secondly, we could make lld provide the 
symbols, to make things with gcc+binutils behave the same as with 
clang+lld, making the CRT object files compatible across both linkers at 
the same time.


// Martin





--
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public


Re: [Mingw-w64-public] [PATCH] crt: Unify and simplify handling of constructor/destructor lists

2018-08-27 Thread Liu Hao
This patch breaks libgcc.

At the moment the `__main()` function which performs global 
initialization for static objects cannot handle `__CTOR_LIST__` with two 
pointers of `-1` in the front of it [1]. The code is presumed to call 
every function via pointers between the first `-1` and final null 
terminator in reverse order, which, if the second element is a 
duplicated `-1`, will result in a segfault at the last iteration of the 
loop.

Probably this patch should be reverted.

[1] https://github.com/gcc-mirror/gcc/blob/master/libgcc/gbl-ctors.h#L75

-- 
Best regards,
LH_Mouse
--
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public


Re: [Mingw-w64-public] [PATCH] crt: Unify and simplify handling of constructor/destructor lists

2018-08-07 Thread Martin Storsjö

On Fri, 3 Aug 2018, Liu Hao wrote:


在 2018-08-03 03:16, Martin Storsjö 写道:

GNU binutils ld traditionally provides __CTOR_LIST__ and __DTOR_LIST__
symbols via a linker script, while lld doesn't.
 (... ...)
-#else
-// old method that iterates the list twice because old linker scripts do 
not have __CTOR_END__


This drops the compatibility with those 'old linker scripts', doesn't it?


(Explained before that it doesn't.)


This patch looks good otherwise.


Thanks, pushed now, after getting the corresponding comment in binutils 
tweaked a little.


// Martin
--
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public


Re: [Mingw-w64-public] [PATCH] crt: Unify and simplify handling of constructor/destructor lists

2018-08-02 Thread Martin Storsjö

On Fri, 3 Aug 2018, Liu Hao wrote:


在 2018-08-03 03:16, Martin Storsjö 写道:

GNU binutils ld traditionally provides __CTOR_LIST__ and __DTOR_LIST__
symbols via a linker script, while lld doesn't.
 (... ...)
-#else
-// old method that iterates the list twice because old linker scripts do 
not have __CTOR_END__


This drops the compatibility with those 'old linker scripts', doesn't it?


No, it's still compatible - we provide our own __CTOR_END__ anyway, which 
is sorted in the right place by the linker due to the section name.


In practice this comment seemed to be a bit misleading, because not even 
the latest binutils provide __CTOR_END__. It does store the terminating 
null pointer here, but it doesn't provide any symbol pointing to it.


// Martin
--
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public


Re: [Mingw-w64-public] [PATCH] crt: Unify and simplify handling of constructor/destructor lists

2018-08-02 Thread Liu Hao
在 2018-08-03 03:16, Martin Storsjö 写道:
> GNU binutils ld traditionally provides __CTOR_LIST__ and __DTOR_LIST__
> symbols via a linker script, while lld doesn't.
>  (... ...)
> -#else
> -// old method that iterates the list twice because old linker scripts do not 
> have __CTOR_END__

This drops the compatibility with those 'old linker scripts', doesn't it?

This patch looks good otherwise.

-- 
Best regards,
LH_Mouse
--
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public


Re: [Mingw-w64-public] [PATCH] crt: Unify and simplify handling of constructor/destructor lists

2018-08-02 Thread JonY via Mingw-w64-public
On 08/02/2018 08:25 PM, Martin Storsjö wrote:
> On Thu, 2 Aug 2018, Liu Hao wrote:
> 
>>> index 54cbf02..44ff653 100644
>>> --- a/mingw-w64-crt/crt/gccmain.c
>>> +++ b/mingw-w64-crt/crt/gccmain.c
>>> @@ -23,18 +23,24 @@ __do_global_dtors (void)
>>>   while (*p)
>>>   {
>>> -  (*(p)) ();
>>> +  // If the linker provided its own __DTOR_LIST__ in addition to
>>> the
>>> +  // one we provide, we'd end up with the first pointer here being
>>> +  // a (func_ptr)-1 sentinel.
>>
>> jon_y used to require all comments be C89-ish. I am not totally clear
>> about the reason. May he elaborate a little.
> 
> I forgot to change this for this patch when I posted the updated
> version, but I changed it for the cxa_atexit patchset before pushing.
> 
> // Martin
> 
>


It's a preference, but not a hard one, seeing though C89 style comments
are supported by all C compliant compilers.


signature.asc
Description: OpenPGP digital signature
--
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public


Re: [Mingw-w64-public] [PATCH] crt: Unify and simplify handling of constructor/destructor lists

2018-08-02 Thread Martin Storsjö

On Thu, 2 Aug 2018, Liu Hao wrote:


index 54cbf02..44ff653 100644
--- a/mingw-w64-crt/crt/gccmain.c
+++ b/mingw-w64-crt/crt/gccmain.c
@@ -23,18 +23,24 @@ __do_global_dtors (void)
  while (*p)
  {
-  (*(p)) ();
+  // If the linker provided its own __DTOR_LIST__ in addition to the
+  // one we provide, we'd end up with the first pointer here being
+  // a (func_ptr)-1 sentinel.


jon_y used to require all comments be C89-ish. I am not totally clear about 
the reason. May he elaborate a little.


I forgot to change this for this patch when I posted the updated version, 
but I changed it for the cxa_atexit patchset before pushing.


// Martin


--
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public


Re: [Mingw-w64-public] [PATCH] crt: Unify and simplify handling of constructor/destructor lists

2018-08-02 Thread Martin Storsjö

On Thu, 2 Aug 2018, Martin Storsjö wrote:


On Thu, 2 Aug 2018, Liu Hao wrote:


在 2018/8/2 19:02, Martin Storsjö 写道:

-#ifdef __clang__
  extern func_ptr __CTOR_END__[];
  extern func_ptr __DTOR_END__[];

  void __do_global_ctors (void)
  {
static func_ptr *p = __CTOR_END__ - 1;
+  // If the linker provided its own __CTOR_LIST__ in addition to the one
+  // we provide, we'd actually stop at __CTOR_LIST__+1, but that's no 

problem

+  // for this function.
while (*p != (func_ptr) -1) {
  (*(p))();


At the very firsts iteration, isn't `*p` null if there are two null 
termini in the list?


(i.e. the list looks like `-1, -1, ... some `func_ptr`s ... , 0, 0`)


I thought the same; that's why I did the extra check with "if (*p)", as I 
mentioned in the other mail.


However, in practice, __CTOR_END__ points to the first 0-terminator. Not 
sure why that is, but you can check with -Wl,-Map,map.txt.


But yes, it's safer with that extra check added, then both iterations 
should be fine, regardless which one the symbol points to, in both ends.


This is because it seems like GNU LD actually never provides any 
__CTOR_END__ symbol. But we can have the extra check in any case, for 
safety and symmetry.


// Martin
--
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public


Re: [Mingw-w64-public] [PATCH] crt: Unify and simplify handling of constructor/destructor lists

2018-08-02 Thread Martin Storsjö

On Thu, 2 Aug 2018, Liu Hao wrote:


在 2018/8/2 19:02, Martin Storsjö 写道:

-#ifdef __clang__
  extern func_ptr __CTOR_END__[];
  extern func_ptr __DTOR_END__[];

  void __do_global_ctors (void)
  {
static func_ptr *p = __CTOR_END__ - 1;
+  // If the linker provided its own __CTOR_LIST__ in addition to the one
+  // we provide, we'd actually stop at __CTOR_LIST__+1, but that's no problem
+  // for this function.
while (*p != (func_ptr) -1) {
  (*(p))();


At the very firsts iteration, isn't `*p` null if there are two null 
termini in the list?


(i.e. the list looks like `-1, -1, ... some `func_ptr`s ... , 0, 0`)


I thought the same; that's why I did the extra check with "if (*p)", as I 
mentioned in the other mail.


However, in practice, __CTOR_END__ points to the first 0-terminator. Not 
sure why that is, but you can check with -Wl,-Map,map.txt.


But yes, it's safer with that extra check added, then both iterations 
should be fine, regardless which one the symbol points to, in both ends.


// Martin
--
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public


Re: [Mingw-w64-public] [PATCH] crt: Unify and simplify handling of constructor/destructor lists

2018-08-02 Thread Liu Hao
在 2018/8/2 19:02, Martin Storsjö 写道:
> -#ifdef __clang__
>   extern func_ptr __CTOR_END__[];
>   extern func_ptr __DTOR_END__[];
>   
>   void __do_global_ctors (void)
>   {
> static func_ptr *p = __CTOR_END__ - 1;
> +  // If the linker provided its own __CTOR_LIST__ in addition to the one
> +  // we provide, we'd actually stop at __CTOR_LIST__+1, but that's no problem
> +  // for this function.
> while (*p != (func_ptr) -1) {
>   (*(p))();

At the very firsts iteration, isn't `*p` null if there are two null 
termini in the list?

(i.e. the list looks like `-1, -1, ... some `func_ptr`s ... , 0, 0`)

>   p--;
> @@ -42,30 +48,6 @@ void __do_global_ctors (void)
> atexit (__do_global_dtors);
>   }
>   



-- 
Best regards,
LH_Mouse
--
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public


Re: [Mingw-w64-public] [PATCH] crt: Unify and simplify handling of constructor/destructor lists

2018-08-02 Thread Martin Storsjö

On Thu, 2 Aug 2018, Liu Hao wrote:


在 2018-08-02 19:02, Martin Storsjö 写道:

Signed-off-by: Martin Storsjö 
---
  mingw-w64-crt/crt/crtdll.c  |  2 --
  mingw-w64-crt/crt/crtexe.c  |  2 --
  mingw-w64-crt/crt/gccmain.c | 34 --
  3 files changed, 8 insertions(+), 30 deletions(-)

diff --git a/mingw-w64-crt/crt/crtdll.c b/mingw-w64-crt/crt/crtdll.c
index 50a9eb4..af69573 100644
--- a/mingw-w64-crt/crt/crtdll.c
+++ b/mingw-w64-crt/crt/crtdll.c
@@ -40,12 +40,10 @@ extern _CRTALLOC(".CRT$XIZ") _PIFV __xi_z[];
  extern _CRTALLOC(".CRT$XCA") _PVFV __xc_a[];
  extern _CRTALLOC(".CRT$XCZ") _PVFV __xc_z[];
  -#ifdef __clang__
  __attribute__ (( __section__ (".ctors"), __used__ , aligned(sizeof(void 
* const void * __CTOR_LIST__ = (void *) -1;
  __attribute__ (( __section__ (".dtors"), __used__ , aligned(sizeof(void 
* const void * __DTOR_LIST__ = (void *) -1;
  __attribute__ (( __section__ (".ctors.9"), __used__ , 
aligned(sizeof(void * const void * __CTOR_END__ = (void *) 0;
  __attribute__ (( __section__ (".dtors.9"), __used__ , 
aligned(sizeof(void * const void * __DTOR_END__ = (void *) 0;

-#endif


Does GNU LD recognize the `.9` suffix?

The known and working way to sort sections for GNU LD for Windows is

   .ctors$
   .ctors$foo
   .ctors$

and such sections are sorted in alphabet order rather than numeric order. 
This could explain why these symbols are not emitted for GCC.


Yes, GNU LD supports it - you get similar things emitted by GCC if you 
specify a constructor priority.


Case example:

$ cat test.cpp

void other(void);

class Foo {
public:
Foo() {
other();
}
};

Foo foo1 __attribute__((init_priority(101)));
Foo foo2 __attribute__((init_priority(65534)));

$ x86_64-w64-mingw32-g++ -S test.cpp -o - -O2 | grep ctors
.section.ctors.65434,"w"
.section.ctors.1,"w"

The number after .ctors is 65535 minus the value specified in 
init_priority. The values are padded to 5 digits with leading zeros, and 
GNU LD sorts them alphabetically when linking, which is equal to numeric 
order when it's zero padded.


Since the values are in the range 0-65535, the sentinel at 9 will 
always be sorted last.



diff --git a/mingw-w64-crt/crt/gccmain.c b/mingw-w64-crt/crt/gccmain.c
index 54cbf02..44ff653 100644
--- a/mingw-w64-crt/crt/gccmain.c
+++ b/mingw-w64-crt/crt/gccmain.c
@@ -23,18 +23,24 @@ __do_global_dtors (void)
  while (*p)
  {
-  (*(p)) ();
+  // If the linker provided its own __DTOR_LIST__ in addition to the
+  // one we provide, we'd end up with the first pointer here being
+  // a (func_ptr)-1 sentinel.


jon_y used to require all comments be C89-ish. I am not totally clear about 
the reason. May he elaborate a little.


I can change them to that style if there's a preference for that - I'll 
not repost any new version of the patch just for that though.


Just to be safe, I'm amending the patch locally like this as well:

@@ -42,7 +42,8 @@ void __do_global_ctors (void)
   // we provide, we'd actually stop at __CTOR_LIST__+1, but that's no problem
   // for this function.
   while (*p != (func_ptr) -1) {
-(*(p))();
+if (*p)
+  (*(p))();
 p--;
   }

That doesn't turn out to be necessary in my testing with GNU LD, but it's 
safer that way.


// Martin
--
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public