Re: [Mingw-w64-public] Patch WS2 Inline Functions
On Tue, 13 Jul 2021, Jonathan Marler wrote: I think the ideal solution would allow programs to take the address of these functions since MSVC allows it. Well even with static inline, their address can be taken just fine, it's just not identical across all translation units. I don't see that as a big issue here, so I'd be fine with going with that approach. // Martin ___ Mingw-w64-public mailing list Mingw-w64-public@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/mingw-w64-public
Re: [Mingw-w64-public] Increasing the stack programmatically on mingw32
On Tue, 13 Jul 2021, Tempelaar E. (Erik) wrote: > For this to work correctly the stack size was increased somewhere in the > past; on Unix using setrlimit, in mingw32 with 'LDFLAGS += > -Wl,--stack,0x0200' (32MiB) > I've seen the "processthreadsapi" and noticed that it has a 'dwStackSize' > parameter and that there's a flag to set it merely as a reservation > 'STACK_SIZE_PARAM_IS_A_RESERVATION' > I guess a reservation would be fine too. The value of --stack is the default reservation. It can optionally take a second number which is the default commit. That's not important to what you are seeing. > Ideally I'd like to get the extra stack only for specific work and not > always, but I don't see how. Yes, you can control the stack size per thread (or fiber). For winpthreads, you can use pthread_attr_setstacksize. ___ 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 WS2 Inline Functions
I think the ideal solution would allow programs to take the address of these functions since MSVC allows it. For this we could either find a version of inline attributes that allows emission and doesn't cause duplicate symbol errors during link, or, keep the headers as they are and provide the the definitions in the library explicitly. On Tue, Jul 13, 2021, 6:55 AM LIU Hao wrote: > 在 7/13/21 6:33 PM, Martin Storsjö 写道: > >> > >> It appears to fix the issue yes. Here's a patch with that solution: > >> > >> > > `static inline` looks the safest solution, as long as the address of those > functions aren't taken. > > > -- > Best regards, > LIU Hao > > ___ > Mingw-w64-public mailing list > Mingw-w64-public@lists.sourceforge.net > https://lists.sourceforge.net/lists/listinfo/mingw-w64-public > ___ Mingw-w64-public mailing list Mingw-w64-public@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/mingw-w64-public
[Mingw-w64-public] [PATCH] headers: Import propvarutil.h from wine
From ad16f9d5f67e64860b09541a7f285e10434c4884 Mon Sep 17 00:00:00 2001 From: Biswapriyo Nath Date: Tue, 13 Jul 2021 21:03:36 +0530 Subject: [PATCH] headers: Import propvarutil.h from wine This reverts d603db2c1544a26c7e1153208b660f1c0f0f21d7 commit. The added functions are required for qt6-multimedia v6.2.0. Signed-off-by: Biswapriyo Nath --- mingw-w64-headers/wine-import.sh | 1 + 1 file changed, 1 insertion(+) diff --git a/mingw-w64-headers/wine-import.sh b/mingw-w64-headers/wine-import.sh index a1b80a8..f0c998f 100755 --- a/mingw-w64-headers/wine-import.sh +++ b/mingw-w64-headers/wine-import.sh @@ -113,6 +113,7 @@ for f in \ mscat.h \ propkeydef.h \ propkey.h \ + propvarutil.h \ rpcsal.h \ t2embapi.h \ uiautomationcoreapi.h \ -- 2.32.0 ___ Mingw-w64-public mailing list Mingw-w64-public@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/mingw-w64-public
[Mingw-w64-public] Increasing the stack programmatically on mingw32
Hello all, The 32-bit application I work on needs to able to validate a long string in XML against a complex regular expression in the XSD (using xerces-c) For this to work correctly the stack size was increased somewhere in the past; on Unix using setrlimit, in mingw32 with 'LDFLAGS += -Wl,--stack,0x0200' (32MiB) However, when creating many (50+) pthreads the system complains about lacking resources (only on Windows), with the following error: pthread_create (11): Not enough memory resources are available to process this command. I believe that's because the application is reaching the 32-bit limits for memory. Ideally I'd like to get the extra stack only for specific work and not always, but I don't see how. I've seen the "processthreadsapi" and noticed that it has a 'dwStackSize' parameter and that there's a flag to set it merely as a reservation 'STACK_SIZE_PARAM_IS_A_RESERVATION' I guess a reservation would be fine too. Any hints on how to resolve this issue? Kind regards, Erik Disclaimer: This mail transmission and any attached files are confidential and are intended for the addressee only. If you are not the person or organization to whom it is addressed, you must not copy, disclose, distribute or take any action in reliance upon it. If you have received this message in error, please contact the sender by email and delete all copies of this message and all copies of any attached files. ___ 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 WS2 Inline Functions
在 7/13/21 6:33 PM, Martin Storsjö 写道: It appears to fix the issue yes. Here's a patch with that solution: `static inline` looks the safest solution, as long as the address of those functions aren't taken. -- Best regards, LIU Hao OpenPGP_signature Description: OpenPGP digital signature ___ 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 WS2 Inline Functions
On Tue, 13 Jul 2021, Jonathan Marler wrote: I highly suggest you not play with this inline stuff. It's something very fragile that works by accident; any tiny change could be catastrophic. Yeah this whole inline thing is a complete mess. But the headers are currently broken with Clang, using any of those WS2TCP_INLINE functions with clang will result in linker errors to unresolved symbols. See the original email/patch for more details, but it appears tha Clang is choosing not to inline some of the calls which makes it incompatible with __gnu_inline__ which disables the function emission altogether. jon_y suggested on IRC that we add these functions to the library itself which may not be a bad idea at this point. It would mean not having to touch these seemingly brittle header files. Do things work out if you use the existing __mingw_ovr attribute define? It appears to fix the issue yes. Here's a patch with that solution: From 8f4c87ad8b19bf904ae0357a09e52477d49abea3 Mon Sep 17 00:00:00 2001 From: Jonathan Marler Date: Tue, 13 Jul 2021 03:37:56 -0600 Subject: [PATCH] Use __mingw_ovr for WS2TCPIP_INLINE --- mingw-w64-headers/include/ws2ipdef.h | 4 ++-- mingw-w64-headers/include/ws2tcpip.h | 36 ++-- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/mingw-w64-headers/include/ws2ipdef.h b/mingw-w64-headers/include/ws2ipdef.h index d440bbcb8..6b10db388 100644 --- a/mingw-w64-headers/include/ws2ipdef.h +++ b/mingw-w64-headers/include/ws2ipdef.h @@ -238,9 +238,9 @@ typedef struct group_source_req { SOCKADDR_STORAGE gsr_source; } GROUP_SOURCE_REQ, *PGROUP_SOURCE_REQ; -#define WS2TCPIP_INLINE __CRT_INLINE +#define WS2TCPIP_INLINE __mingw_ovr -int IN6_ADDR_EQUAL(const struct in6_addr *,const struct in6_addr *); +static int IN6_ADDR_EQUAL(const struct in6_addr *,const struct in6_addr *); WS2TCPIP_INLINE int IN6_ADDR_EQUAL(const struct in6_addr *a, const struct in6_addr *b) { return !memcmp(a, b, sizeof(struct in6_addr)); } diff --git a/mingw-w64-headers/include/ws2tcpip.h b/mingw-w64-headers/include/ws2tcpip.h index 0a7890bb3..cf7d28ba6 100644 --- a/mingw-w64-headers/include/ws2tcpip.h +++ b/mingw-w64-headers/include/ws2tcpip.h @@ -46,24 +46,24 @@ extern "C" { extern const struct in6_addr in6addr_any; extern const struct in6_addr in6addr_loopback; -int IN6_IS_ADDR_UNSPECIFIED(const struct in6_addr *); -int IN6_IS_ADDR_LOOPBACK(const struct in6_addr *); -int IN6_IS_ADDR_MULTICAST(const struct in6_addr *); -int IN6_IS_ADDR_LINKLOCAL(const struct in6_addr *); -int IN6_IS_ADDR_SITELOCAL(const struct in6_addr *); -int IN6_IS_ADDR_V4MAPPED(const struct in6_addr *); -int IN6_IS_ADDR_V4COMPAT(const struct in6_addr *); -int IN6_IS_ADDR_MC_NODELOCAL(const struct in6_addr *); -int IN6_IS_ADDR_MC_LINKLOCAL(const struct in6_addr *); -int IN6_IS_ADDR_MC_SITELOCAL(const struct in6_addr *); -int IN6_IS_ADDR_MC_ORGLOCAL(const struct in6_addr *); -int IN6_IS_ADDR_MC_GLOBAL(const struct in6_addr *); -int IN6ADDR_ISANY(const struct sockaddr_in6 *); -int IN6ADDR_ISLOOPBACK(const struct sockaddr_in6 *); -void IN6_SET_ADDR_UNSPECIFIED(struct in6_addr *); -void IN6_SET_ADDR_LOOPBACK(struct in6_addr *); -void IN6ADDR_SETANY(struct sockaddr_in6 *); -void IN6ADDR_SETLOOPBACK(struct sockaddr_in6 *); +static int IN6_IS_ADDR_UNSPECIFIED(const struct in6_addr *); +static int IN6_IS_ADDR_LOOPBACK(const struct in6_addr *); Oh, tricky, so we do actually have non-static declarations of them, which does sound like an expectation to have them globally available somewhere - that we're failing to fulfill. Then we could indeed try to provide that too, but that leads to duplicate implementations of those functions... Hmm. I don't think I have a direct preference among these alternatives - let's see what others think. In practice, all of these functions are "nonstandard" (not like the C standard that says that "printf" must exist as a non-static symbol) and all fairly small/trivial so it shouldn't really matter much exactly which way we go. // Martin ___ 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 WS2 Inline Functions
> I highly suggest you not play with this inline stuff. It's something very fragile that works by accident; any tiny change could be catastrophic. Yeah this whole inline thing is a complete mess. But the headers are currently broken with Clang, using any of those WS2TCP_INLINE functions with clang will result in linker errors to unresolved symbols. See the original email/patch for more details, but it appears tha Clang is choosing not to inline some of the calls which makes it incompatible with __gnu_inline__ which disables the function emission altogether. jon_y suggested on IRC that we add these functions to the library itself which may not be a bad idea at this point. It would mean not having to touch these seemingly brittle header files. > Do things work out if you use the existing __mingw_ovr attribute define? It appears to fix the issue yes. Here's a patch with that solution: From 8f4c87ad8b19bf904ae0357a09e52477d49abea3 Mon Sep 17 00:00:00 2001 From: Jonathan Marler Date: Tue, 13 Jul 2021 03:37:56 -0600 Subject: [PATCH] Use __mingw_ovr for WS2TCPIP_INLINE --- mingw-w64-headers/include/ws2ipdef.h | 4 ++-- mingw-w64-headers/include/ws2tcpip.h | 36 ++-- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/mingw-w64-headers/include/ws2ipdef.h b/mingw-w64-headers/include/ws2ipdef.h index d440bbcb8..6b10db388 100644 --- a/mingw-w64-headers/include/ws2ipdef.h +++ b/mingw-w64-headers/include/ws2ipdef.h @@ -238,9 +238,9 @@ typedef struct group_source_req { SOCKADDR_STORAGE gsr_source; } GROUP_SOURCE_REQ, *PGROUP_SOURCE_REQ; -#define WS2TCPIP_INLINE __CRT_INLINE +#define WS2TCPIP_INLINE __mingw_ovr -int IN6_ADDR_EQUAL(const struct in6_addr *,const struct in6_addr *); +static int IN6_ADDR_EQUAL(const struct in6_addr *,const struct in6_addr *); WS2TCPIP_INLINE int IN6_ADDR_EQUAL(const struct in6_addr *a, const struct in6_addr *b) { return !memcmp(a, b, sizeof(struct in6_addr)); } diff --git a/mingw-w64-headers/include/ws2tcpip.h b/mingw-w64-headers/include/ws2tcpip.h index 0a7890bb3..cf7d28ba6 100644 --- a/mingw-w64-headers/include/ws2tcpip.h +++ b/mingw-w64-headers/include/ws2tcpip.h @@ -46,24 +46,24 @@ extern "C" { extern const struct in6_addr in6addr_any; extern const struct in6_addr in6addr_loopback; -int IN6_IS_ADDR_UNSPECIFIED(const struct in6_addr *); -int IN6_IS_ADDR_LOOPBACK(const struct in6_addr *); -int IN6_IS_ADDR_MULTICAST(const struct in6_addr *); -int IN6_IS_ADDR_LINKLOCAL(const struct in6_addr *); -int IN6_IS_ADDR_SITELOCAL(const struct in6_addr *); -int IN6_IS_ADDR_V4MAPPED(const struct in6_addr *); -int IN6_IS_ADDR_V4COMPAT(const struct in6_addr *); -int IN6_IS_ADDR_MC_NODELOCAL(const struct in6_addr *); -int IN6_IS_ADDR_MC_LINKLOCAL(const struct in6_addr *); -int IN6_IS_ADDR_MC_SITELOCAL(const struct in6_addr *); -int IN6_IS_ADDR_MC_ORGLOCAL(const struct in6_addr *); -int IN6_IS_ADDR_MC_GLOBAL(const struct in6_addr *); -int IN6ADDR_ISANY(const struct sockaddr_in6 *); -int IN6ADDR_ISLOOPBACK(const struct sockaddr_in6 *); -void IN6_SET_ADDR_UNSPECIFIED(struct in6_addr *); -void IN6_SET_ADDR_LOOPBACK(struct in6_addr *); -void IN6ADDR_SETANY(struct sockaddr_in6 *); -void IN6ADDR_SETLOOPBACK(struct sockaddr_in6 *); +static int IN6_IS_ADDR_UNSPECIFIED(const struct in6_addr *); +static int IN6_IS_ADDR_LOOPBACK(const struct in6_addr *); +static int IN6_IS_ADDR_MULTICAST(const struct in6_addr *); +static int IN6_IS_ADDR_LINKLOCAL(const struct in6_addr *); +static int IN6_IS_ADDR_SITELOCAL(const struct in6_addr *); +static int IN6_IS_ADDR_V4MAPPED(const struct in6_addr *); +static int IN6_IS_ADDR_V4COMPAT(const struct in6_addr *); +static int IN6_IS_ADDR_MC_NODELOCAL(const struct in6_addr *); +static int IN6_IS_ADDR_MC_LINKLOCAL(const struct in6_addr *); +static int IN6_IS_ADDR_MC_SITELOCAL(const struct in6_addr *); +static int IN6_IS_ADDR_MC_ORGLOCAL(const struct in6_addr *); +static int IN6_IS_ADDR_MC_GLOBAL(const struct in6_addr *); +static int IN6ADDR_ISANY(const struct sockaddr_in6 *); +static int IN6ADDR_ISLOOPBACK(const struct sockaddr_in6 *); +static void IN6_SET_ADDR_UNSPECIFIED(struct in6_addr *); +static void IN6_SET_ADDR_LOOPBACK(struct in6_addr *); +static void IN6ADDR_SETANY(struct sockaddr_in6 *); +static void IN6ADDR_SETLOOPBACK(struct sockaddr_in6 *); WS2TCPIP_INLINE int IN6_IS_ADDR_UNSPECIFIED(const struct in6_addr *a) { return ((a->s6_words[0]==0) && (a->s6_words[1]==0) && (a->s6_words[2]==0) && (a->s6_words[3]==0) && (a->s6_words[4]==0) && (a->s6_words[5]==0) && (a->s6_words[6]==0) && (a->s6_words[7]==0)); } WS2TCPIP_INLINE int IN6_IS_ADDR_LOOPBACK(const struct in6_addr *a) { return ((a->s6_words[0]==0) && (a->s6_words[1]==0) && (a->s6_words[2]==0) && (a->s6_words[3]==0) && (a->s6_words[4]==0) && (a->s6_words[5]==0) && (a->s6_words[6]==0) && (a->s6_words[7]==0x0100)); } -- 2.25.4 On Tue, Jul 13, 2021 at 3:31 AM Martin Storsjö wrote: > On Tue, 13 Jul 2021, LIU Hao wrote: > > > 在 7/13/21 5:02 PM, Jonatha
Re: [Mingw-w64-public] Patch WS2 Inline Functions
On Tue, 13 Jul 2021, LIU Hao wrote: 在 7/13/21 5:02 PM, Jonathan Marler 写道: Thanks for the convenient info. However, when I try to use __attribute__((__weak__)) I get a compiler warning from GCC, i.e. extern __inline__ __attribute__((__weak__)) void foo(void) {} int main(int argc, char *argv[]) { foo(); } $ gcc main.c main.c:2:10: warning: inline function ‘foo’ declared weak [-Wattributes] 2 | void foo(void) {} | ^~~ I'm having a hard time figuring out why I get this warning. The info you sent looks consistent with the docs I'm finding, but this warning makes it look like GCC thinks the "weak" attribute is redundant? Note that I still get this same warning if I remove the "extern", so it seems like GCC doesn't like inline and the weak attribute...any idea why? (Please *Reply to All*.) There must have been reasons why GCC ignores `weak` attribute on inline functions [1]. It might be technical limitation, but I think it makes no sense, because 1) Clang accepts, and 2) decomposing the two attributes actually works as expected [2]. Overall I'd suggest to avoid using `weak` if it's possible; it's kinda tricky/messy on COFF targets, and IIRC there's a number of cases with GCC/binutils where it doesn't quite work as you'd want to. (On ELF it's robust though.) Do things work out if you use the existing __mingw_ovr attribute define? That one iirc expands to something which is always inlined and doesn't expect any global definition. // Martin ___ 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 WS2 Inline Functions
在 7/13/21 5:02 PM, Jonathan Marler 写道: Thanks for the convenient info. However, when I try to use __attribute__((__weak__)) I get a compiler warning from GCC, i.e. extern __inline__ __attribute__((__weak__)) void foo(void) {} int main(int argc, char *argv[]) { foo(); } $ gcc main.c main.c:2:10: warning: inline function ‘foo’ declared weak [-Wattributes] 2 | void foo(void) {} | ^~~ I'm having a hard time figuring out why I get this warning. The info you sent looks consistent with the docs I'm finding, but this warning makes it look like GCC thinks the "weak" attribute is redundant? Note that I still get this same warning if I remove the "extern", so it seems like GCC doesn't like inline and the weak attribute...any idea why? (Please *Reply to All*.) There must have been reasons why GCC ignores `weak` attribute on inline functions [1]. It might be technical limitation, but I think it makes no sense, because 1) Clang accepts, and 2) decomposing the two attributes actually works as expected [2]. I highly suggest you not play with this inline stuff. It's something very fragile that works by accident; any tiny change could be catastrophic. [1] https://gcc.godbolt.org/z/ssEz9Gddo [2] https://gcc.godbolt.org/z/Prcenddoc -- Best regards, LIU Hao OpenPGP_signature Description: OpenPGP digital signature ___ Mingw-w64-public mailing list Mingw-w64-public@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/mingw-w64-public
[Mingw-w64-public] [PATCH] crt: Fix printf formatting of %a on arm/aarch64 with __USE_MINGW_ANSI_STDIO
The mingw_pformat.c code converts all input floats to an 80 bit float representation and analyzes that struct when printing the float. This was already fixed in ceb4c4fd4b696e96bbe174ce4abc065d43e9ac87, but one case in was missed. Factorize the conversion from 64 to 80 bit floats to a function used to intialize the __pformat_fpreg_t struct. Signed-off-by: Martin Storsjö --- mingw-w64-crt/stdio/mingw_pformat.c | 46 - 1 file changed, 26 insertions(+), 20 deletions(-) diff --git a/mingw-w64-crt/stdio/mingw_pformat.c b/mingw-w64-crt/stdio/mingw_pformat.c index b1c139bbe..b80150af3 100644 --- a/mingw-w64-crt/stdio/mingw_pformat.c +++ b/mingw-w64-crt/stdio/mingw_pformat.c @@ -1048,28 +1048,23 @@ typedef union */ #include "../gdtoa/gdtoa.h" -static -char *__pformat_cvt( int mode, __pformat_fpreg_t x, int nd, int *dp, int *sign ) +static __pformat_fpreg_t init_fpreg_ldouble( long double val ) { - /* Helper function, derived from David M. Gay's `g_xfmt()', calling - * his `__gdtoa()' function in a manner to provide extended precision - * replacements for `ecvt()' and `fcvt()'. - */ - int k; unsigned int e = 0; char *ep; - static FPI fpi = { 64, 1-16383-64+1, 32766-16383-64+1, FPI_Round_near, 0, 14 /* Int_max */ }; - + __pformat_fpreg_t x; + x.__pformat_fpreg_ldouble_t = val; + if( sizeof( double ) == sizeof( long double ) ) { -/* The caller has written into x.__pformat_fpreg_ldouble_t, which - * actually isn't laid out in the way the rest of the union expects it. +/* Here, __pformat_fpreg_t expects to be initialized with a 80 bit long + * double, but this platform doesn't have long doubles that differ from + * regular 64 bit doubles. Therefore manually convert the 64 bit float + * value to an 80 bit float value. */ int exp = (x.__pformat_fpreg_mantissa >> 52) & 0x7ff; unsigned long long mant = x.__pformat_fpreg_mantissa & 0x000fULL; int integer = exp ? 1 : 0; int signbit = x.__pformat_fpreg_mantissa >> 63; -k = __fpclassify( x.__pformat_fpreg_double_t ); - if (exp == 0x7ff) exp = 0x7fff; else if (exp != 0) @@ -1077,9 +1072,22 @@ char *__pformat_cvt( int mode, __pformat_fpreg_t x, int nd, int *dp, int *sign ) x.__pformat_fpreg_mantissa = (mant << 11) | ((unsigned long long)integer << 63); x.__pformat_fpreg_exponent = exp | (signbit << 15); } - else -k = __fpclassifyl( x.__pformat_fpreg_ldouble_t ); + return x; +} + +static +char *__pformat_cvt( int mode, long double val, int nd, int *dp, int *sign ) +{ + /* Helper function, derived from David M. Gay's `g_xfmt()', calling + * his `__gdtoa()' function in a manner to provide extended precision + * replacements for `ecvt()' and `fcvt()'. + */ + int k; unsigned int e = 0; char *ep; + static FPI fpi = { 64, 1-16383-64+1, 32766-16383-64+1, FPI_Round_near, 0, 14 /* Int_max */ }; + __pformat_fpreg_t x = init_fpreg_ldouble( val ); + + k = __fpclassifyl( val ); /* Classify the argument into an appropriate `__gdtoa()' category... */ @@ -1130,8 +1138,7 @@ char *__pformat_ecvt( long double x, int precision, int *dp, int *sign ) /* A convenience wrapper for the above... * it emulates `ecvt()', but takes a `long double' argument. */ - __pformat_fpreg_t z; z.__pformat_fpreg_ldouble_t = x; - return __pformat_cvt( 2, z, precision, dp, sign ); + return __pformat_cvt( 2, x, precision, dp, sign ); } static @@ -1140,8 +1147,7 @@ char *__pformat_fcvt( long double x, int precision, int *dp, int *sign ) /* A convenience wrapper for the above... * it emulates `fcvt()', but takes a `long double' argument. */ - __pformat_fpreg_t z; z.__pformat_fpreg_ldouble_t = x; - return __pformat_cvt( 3, z, precision, dp, sign ); + return __pformat_cvt( 3, x, precision, dp, sign ); } /* The following are required, to clean up the `__gdtoa()' memory pool, @@ -2259,7 +2265,7 @@ void __pformat_xldouble( long double x, __pformat_t *stream ) * value specified as `long double' type). */ unsigned sign_bit = 0; - __pformat_fpreg_t z; z.__pformat_fpreg_ldouble_t = x; + __pformat_fpreg_t z = init_fpreg_ldouble( x ); /* First check for NaN; it is emitted unsigned... */ -- 2.25.1 ___ 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 WS2 Inline Functions
在 7/13/21 3:05 PM, Jonathan Marler 写道: +# if ((__MINGW_GNUC_PREREQ(4, 3) || defined(__clang__)) && __STDC_VERSION__ >= 199901L) +# define __MSVC_INLINE extern inline +# else No this is not correct. MSVC `__inline` is the C++ `inline`, which is equivalent to `extern __inline__ __attribute__((__weak__))`. GNUC99C++ plain [1] G N G- static L L L extern [1] N G G- - GNU = `__attribute__((__gnu_inline__)) inline` - C99 = C99 `inline` - C++ = C++ `inline` and MSVC `__inline` [3] * N= no code generated, even when address taken * L= local code, not visible elsewhere * G= global code [2] * G- = weak/linkonce global code [1] `inline void foo() { }` followed by `extern void foo();` is equivalent to `extern inline void foo() { }`. [2] Multiple copies of such code will cause a linker error. [3] Code is generated only in case of inline failure. -- Best regards, LIU Hao OpenPGP_signature Description: OpenPGP digital signature ___ 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 WS2 Inline Functions
That is a good point. Thanks for your help/guidance with this. Here's a new patch where I've copied __CRT_INLINE and created a new __MSVC_INLINE which is meant to behave like the origin MSVC inline From fb39d994898b00ae52106b72f6c835821ae2b455 Mon Sep 17 00:00:00 2001 From: Jonathan Marler Date: Tue, 13 Jul 2021 00:01:03 -0600 Subject: [PATCH] Define __MSVC_INLINE for inline functions that can be emitted The following example works with MSVC but will fail using the mingw headers: #include int main(int argc, char **argv) { return (int)&IN6_IS_ADDR_UNSPECIFIED; } The reason for this is because MinGW is defining this `IN6_IS_ADDR_UNSPECIFIED` function with `extern inline __attribute__((__gnu_inline__))`. A function defined with these attributes will NEVER be emitted. This means you cannot take the address of the function and if the compiler does not inline a call to it, then you'll get a linker error. In the Windows SDK in ws2ipdef.h, this function uses the `__inline` attribute https://docs.microsoft.com/en-us/cpp/cpp/inline-functions-cpp?view=msvc-160 > This keyword tells the compiler that inline expansion is preferred. However, the compiler > can create a separate instance of the function (instantiate) and create standard calling > linkages instead of inserting the code inline. Two cases where this behavior can happen are: > * Recursive Functions > * Functions that are referred to through a pointer elsewhere in the translation unit. Note that this function is not defined in any .lib or .dll file in the Windows sdk and/or runtime, so the only way to be able to take the address of it from the example above is if the compiler is able to emit the function, or if it's defined elsewhere. The problem here appears to be the inclusion of `__attribute__((__gnu_inline__))` which is what tells the compiler NEVER to emit the function definition. Removing this attribute allows the compiler to emit the function which allows its address to be taken, and prevents linker errors if the compiler decides not to inline a call to it. Note that this applies to multiple functions in the ws2 header files. To fix this, I've created a new __MSVC_INLINE that behaves like the MSVC version of inline and redefined the WS2 functions with this inline attribute instead of __CRT_INLINE. Signed-off-by: Jonathan Marler --- mingw-w64-headers/crt/_mingw.h.in| 13 + mingw-w64-headers/include/ws2ipdef.h | 2 +- 2 files changed, 14 insertions(+), 1 deletion(-) diff --git a/mingw-w64-headers/crt/_mingw.h.in b/mingw-w64-headers/crt/_ mingw.h.in index b7fb99f42..2bbd2b611 100644 --- a/mingw-w64-headers/crt/_mingw.h.in +++ b/mingw-w64-headers/crt/_mingw.h.in @@ -93,6 +93,19 @@ limitations in handling dllimport attribute. */ # endif #endif +/*__MSVC_INLINE: like MSVC's inline, compiler may emit the function being defined */ +#ifdef __cplusplus +# define __MSVC_INLINE inline +#elif defined(_MSC_VER) +# define __MSVC_INLINE __inline +#else +# if ((__MINGW_GNUC_PREREQ(4, 3) || defined(__clang__)) && __STDC_VERSION__ >= 199901L) +# define __MSVC_INLINE extern inline +# else +# define __MSVC_INLINE extern __inline__ +# endif +#endif + #if !defined(__MINGW_INTRIN_INLINE) && defined(__GNUC__) #define __MINGW_INTRIN_INLINE extern __inline__ __attribute__((__always_inline__,__gnu_inline__)) #endif diff --git a/mingw-w64-headers/include/ws2ipdef.h b/mingw-w64-headers/include/ws2ipdef.h index d440bbcb8..e45163949 100644 --- a/mingw-w64-headers/include/ws2ipdef.h +++ b/mingw-w64-headers/include/ws2ipdef.h @@ -238,7 +238,7 @@ typedef struct group_source_req { SOCKADDR_STORAGE gsr_source; } GROUP_SOURCE_REQ, *PGROUP_SOURCE_REQ; -#define WS2TCPIP_INLINE __CRT_INLINE +#define WS2TCPIP_INLINE __MSVC_INLINE int IN6_ADDR_EQUAL(const struct in6_addr *,const struct in6_addr *); WS2TCPIP_INLINE int IN6_ADDR_EQUAL(const struct in6_addr *a, const struct in6_addr *b) { -- 2.25.4 On Tue, Jul 13, 2021 at 12:50 AM Martin Storsjö wrote: > Hi Jonathan, > > On Tue, 13 Jul 2021, Jonathan Marler wrote: > > > The problem here appears to be the inclusion of > > `__attribute__((__gnu_inline__))` which is what > > tells the compiler NEVER to emit the function definition. Removing this > > attribute allows the compiler > > to emit the function which allows its address to be taken, and prevents > > linker errors if the compiler > > decides not to inline a call to it. > > > > Note that this applies to multiple functions in the ws2 header files. > > > > Signed-off-by: Jonathan Marler > > --- > > mingw-w64-headers/crt/_mingw.h.in | 2 +- > > 1 file changed, 1 insertion(+), 1 deletion(-) > > > > diff --git a/mingw-w64-headers/crt/_mingw.h.in b/mingw-w64-headers/crt/_ > > mingw.h.in > > index b7fb99f42..002079910 100644 > > --- a/mingw-w64-headers/crt/_mingw.h.in > > +++ b/mingw-w64-headers/crt/_mingw.h.in > > @@ -87,7 +87,7 @@ limitations in handling dllimport attribute. */ > > # define __CRT_INLINE __inlin