* Possibly wrong address passed to callq asm instruction within MPIR test binaries @ 2014-04-01 22:07 Jean-Pierre Flori 2014-04-02 9:07 ` Corinna Vinschen 2014-04-03 13:02 ` Jean-Pierre Flori 0 siblings, 2 replies; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-01 22:07 UTC (permalink / raw) To: cygwin; +Cc: Bill Hart Dear all, It's amazing to see how well Cygwin64 is going. Thanks for your hard work. While preparing the new MPIR release, which will be the first one to support Cygwin4, we encountered problems running MPIR testsuite when MPIR was configured to produce a shared lib. That's with latest cygwin/binutils/gcc/g++ from today. It seems that a call to the MPN_ZERO macro, which on my setup is at 0x4ff2746c0 in the shared lib but we get the instruction: callq 0xff2746c0 within the test binary and that yields a nice segfault. Please see https://groups.google.com/d/msg/mpir-devel/KzsxIWhVx8A/EAUoP4ybWOMJ and the few following post for more details. For sure, we don't get what's going on here. Would you have any clue? Might ld decide for some reason to trim the macro address to 4 bytes rather than 8? Best, -- Jean-Pierre Flori -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-01 22:07 Possibly wrong address passed to callq asm instruction within MPIR test binaries Jean-Pierre Flori @ 2014-04-02 9:07 ` Corinna Vinschen 2014-04-06 20:20 ` Jean-Pierre Flori 2014-04-03 13:02 ` Jean-Pierre Flori 1 sibling, 1 reply; 21+ messages in thread From: Corinna Vinschen @ 2014-04-02 9:07 UTC (permalink / raw) To: cygwin [-- Attachment #1: Type: text/plain, Size: 1492 bytes --] On Apr 2 00:07, Jean-Pierre Flori wrote: > Dear all, > > It's amazing to see how well Cygwin64 is going. > Thanks for your hard work. > > While preparing the new MPIR release, which will be the first one to > support Cygwin4, we encountered problems running MPIR testsuite when > MPIR was configured to produce a shared lib. > That's with latest cygwin/binutils/gcc/g++ from today. > > It seems that a call to the MPN_ZERO macro, which on my setup is at > 0x4ff2746c0 in the shared lib but we get the instruction: > callq 0xff2746c0 This looks suspicious. On x86_64 this kind of instruction is usually PC-relative or uses a jump table, because x86_64 uses the small code model by default (medium model on Cygwin). > within the test binary and that yields a nice segfault. > Please see https://groups.google.com/d/msg/mpir-devel/KzsxIWhVx8A/EAUoP4ybWOMJ > and the few following post for more details. > > For sure, we don't get what's going on here. > Would you have any clue? Not without a more detailed report. The aforementioned link does not contain pointers to the source, for instance. Also, a simple testcase might be helpful. If you suspect a linker bug, you might contemplate to ask on the binutils mailing list binutils AT sourceware DOT org which is where ld is maintained. Corinna -- Corinna Vinschen Please, send mails regarding Cygwin to Cygwin Maintainer cygwin AT cygwin DOT com Red Hat [-- Attachment #2: Type: application/pgp-signature, Size: 819 bytes --] ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-02 9:07 ` Corinna Vinschen @ 2014-04-06 20:20 ` Jean-Pierre Flori 2014-04-07 7:52 ` Achim Gratz 2014-04-07 8:43 ` Corinna Vinschen 0 siblings, 2 replies; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-06 20:20 UTC (permalink / raw) To: cygwin Dear all, Le Wed, 02 Apr 2014 11:07:50 +0200, Corinna Vinschen a écrit : > On Apr 2 00:07, Jean-Pierre Flori wrote: >> Dear all, >> >> It's amazing to see how well Cygwin64 is going. >> Thanks for your hard work. >> >> While preparing the new MPIR release, which will be the first one to >> support Cygwin4, we encountered problems running MPIR testsuite when >> MPIR was configured to produce a shared lib. >> That's with latest cygwin/binutils/gcc/g++ from today. >> >> It seems that a call to the MPN_ZERO macro, which on my setup is at >> 0x4ff2746c0 in the shared lib but we get the instruction: >> callq 0xff2746c0 > > This looks suspicious. On x86_64 this kind of instruction is usually > PC-relative or uses a jump table, because x86_64 uses the small code > model by default (medium model on Cygwin). > >> within the test binary and that yields a nice segfault. >> Please see >> https://groups.google.com/d/msg/mpir-devel/KzsxIWhVx8A/EAUoP4ybWOMJ and >> the few following post for more details. >> >> For sure, we don't get what's going on here. >> Would you have any clue? > > Not without a more detailed report. The aforementioned link does not > contain pointers to the source, for instance. Also, a simple testcase > might be helpful. > > If you suspect a linker bug, you might contemplate to ask on the > binutils mailing list binutils AT sourceware DOT org which is where ld > is maintained. > Here come more details as I've taken a little more time to try to understand what was happening. The problem arosed when running the tests for MPIR. The latest alpha is available at http://mpir.org/ Currently it's 2.7.alpha4: http://mpir.org/mpir-2.7.0-alpha4.tar.bz2 Note that thanks to your kind support, MPIR should now build correctly on Cygwin64 (with or without C++ support). That's already great! (And that might help you to take a look at our problem if you feel inclined to do it.) The problem we recently encountered was the following: in gmp-impl.h, mpn_store (which can be either a macro or a function if efficient assembly is available, and so is always a function on x86_64) was not marked __declspec(dllexport/dllimport). (See https://github.com/wbhart/mpir/blob/master/gmp-impl.h#L2419 for the current version with the __GMP_DECLSPEC, defined in mpir.h (from gmp- h.in) where this gets defined as __declspec(dllimport) for the user visible header and use outside of MPIR itself) It seems that because of this lack, the call to mpn_store from a bunch of test executables produced the wrong callq instruction. Once we added the __GMP_DECLSPEC the function got correctly called. What I don't really get is that from what I've read e.g. here : https:// access.redhat.com/site/documentation/en-US/Red_Hat_Enterprise_Linux/4/ html/Using_ld_the_GNU_Linker/win32.html is that the dllimport/export should not be needed anymore. So I took a slightly deeper look and played with the definition of __GMP_DECLSPEC in gmp-h.in/mpir.h to be empty or __declspec(dllexport/ import). The library was built with: ./configure --disable-static --enable-shared make make check (-> potential segfaults when testing the mpn dir) As far as dllexport is concerned, we pass --export-all-symbols to ld, and as expected, we don't need the dllexport part when building the library (we get __imp_ and __nm_ symbols for functions). But it seems that the --enable-auto-import counterpart (which should be ld default) is defeated. I've had a look at the assembly and objects produced by gcc before linking and they indeed look different. With the dllimport magic, I get in t-neg.s: movq %rax, %rcx movq __imp___gmpn_store(%rip), %rax call *%rax Without it I get: movq %rax, %rcx call __gmpn_store Similar differences in the object file (t-neg.o). Looking at the exes produced (.libs/t-neg.exe) gives with the dllimport magic: 100401115: 48 89 c1 mov %rax,%rcx 100401118: 48 8b 05 f1 71 00 00 mov 0x71f1(%rip),%rax # 100408310 <__imp___gmpn_store> 10040111f: ff d0 callq *%rax Without it: 100401111: 48 89 c1 mov %rax,%rcx 100401114: e8 f7 71 00 00 callq 100408310 <__imp___gmpn_store> I've tested the same modifications on Cygwin32 and not putting in the dllimport stuff (or if you prefer, defining __GMP_DECLSPEC to be empty) is no problem. Let's go through the same t-neg file, but use another function as mpn_store is a macro on my 32 bit Cygwin. In assembly with dllimport: movl %eax, (%esp) movl __imp____gmp_randinit_default, %eax call *%eax without dllimport: movl %eax, (%esp) call ___gmp_randinit_default In object file: 23: 89 04 24 mov %eax,(%esp) 26: a1 00 00 00 00 mov 0x0,%eax 2b: ff d0 call *%eax vs: 23: 89 04 24 mov %eax,(%esp) 26: e8 00 00 00 00 call 2b <_main+0x2b> In exe file: 4011b3: 89 04 24 mov %eax,(%esp) 4011b6: a1 74 71 40 00 mov 0x407174,%eax 4011bb: ff d0 call *%eax vs: 4011b3: 89 04 24 mov %eax,(%esp) 4011b6: e8 8d 13 00 00 call 402548 <___gmp_randinit_default> I'm also trying to get GCC 4.7.3 rebuilt to see if it makes any difference with GCC 4.8.2. Any advice would be welcomed! Best, JP -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-06 20:20 ` Jean-Pierre Flori @ 2014-04-07 7:52 ` Achim Gratz 2014-04-07 8:43 ` Corinna Vinschen 1 sibling, 0 replies; 21+ messages in thread From: Achim Gratz @ 2014-04-07 7:52 UTC (permalink / raw) To: cygwin Jean-Pierre Flori writes: > The problem we recently encountered was the following: > in gmp-impl.h, mpn_store (which can be either a macro or a function if > efficient assembly is available, and so is always a function on x86_64) > was not marked __declspec(dllexport/dllimport). I can confirm that GMP has the same problem when I patch out these attributes (which I wanted to do because these cause lots of spurious warnings during compilation). This works fine on 32bit, but produces segmentation faults in some (not all) 64bit test binaries. Regards, Achim. -- +<[Q+ Matrix-12 WAVE#46+305 Neuron microQkb Andromeda XTk Blofeld]>+ Factory and User Sound Singles for Waldorf rackAttack: http://Synth.Stromeko.net/Downloads.html#WaldorfSounds -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-06 20:20 ` Jean-Pierre Flori 2014-04-07 7:52 ` Achim Gratz @ 2014-04-07 8:43 ` Corinna Vinschen 2014-04-07 9:14 ` Jean-Pierre Flori 1 sibling, 1 reply; 21+ messages in thread From: Corinna Vinschen @ 2014-04-07 8:43 UTC (permalink / raw) To: cygwin [-- Attachment #1: Type: text/plain, Size: 4688 bytes --] On Apr 6 20:20, Jean-Pierre Flori wrote: > [...] > The problem we recently encountered was the following: > in gmp-impl.h, mpn_store (which can be either a macro or a function if > efficient assembly is available, and so is always a function on x86_64) > was not marked __declspec(dllexport/dllimport). > (See https://github.com/wbhart/mpir/blob/master/gmp-impl.h#L2419 for the > current version with the __GMP_DECLSPEC, defined in mpir.h (from gmp- > h.in) where this gets defined as __declspec(dllimport) for the user > visible header and use outside of MPIR itself) > It seems that because of this lack, the call to mpn_store from a bunch of > test executables produced the wrong callq instruction. > Once we added the __GMP_DECLSPEC the function got correctly called. > > What I don't really get is that from what I've read e.g. here : https:// > access.redhat.com/site/documentation/en-US/Red_Hat_Enterprise_Linux/4/ > html/Using_ld_the_GNU_Linker/win32.html > is that the dllimport/export should not be needed anymore. And in fact it isn't. > So I took a slightly deeper look and played with the definition of > __GMP_DECLSPEC in gmp-h.in/mpir.h to be empty or __declspec(dllexport/ > import). > The library was built with: > ./configure --disable-static --enable-shared > make > make check (-> potential segfaults when testing the mpn dir) > > As far as dllexport is concerned, we pass --export-all-symbols to ld, and > as expected, we don't need the dllexport part when building the library > (we get __imp_ and __nm_ symbols for functions). > > But it seems that the --enable-auto-import counterpart (which should be > ld default) is defeated. > I've had a look at the assembly and objects produced by gcc before linking > and they indeed look different. > With the dllimport magic, I get in t-neg.s: > movq %rax, %rcx > movq __imp___gmpn_store(%rip), %rax > call *%rax > Without it I get: > movq %rax, %rcx > call __gmpn_store > Similar differences in the object file (t-neg.o). > Looking at the exes produced (.libs/t-neg.exe) gives with the dllimport > magic: > 100401115: 48 89 c1 mov %rax,%rcx > 100401118: 48 8b 05 f1 71 00 00 mov 0x71f1(%rip),%rax # > 100408310 <__imp___gmpn_store> > 10040111f: ff d0 callq *%rax > Without it: > 100401111: 48 89 c1 mov %rax,%rcx > 100401114: e8 f7 71 00 00 callq 100408310 > <__imp___gmpn_store> This is ok. Look closely at the address after the callq. It's the start address of the executable (0x1:00400000) plus an offset. If you disassemble the executable you will find a jmp statement at this address. This is the trampoline code which is automatically generated for external references if they are not marked with dllimport. The problem at this point is that I can't reproduce your issue with a simple example. Here's the example: ==== SNIP ==== $ cat > lib.c <<EOF #include <stdio.h> int foo (int a) { printf ("a = %d\n", a); return a; } EOF $ cat > app.c <<EOF #include <stdio.h> extern int foo (int); int main () { int x = foo (42); printf ("x = %d\n", x); return 0; } EOF $ gcc -g -shared -o lib.dll lib.c $ gcc -g -o app app.c lib.dll $ ./app a = 42 x = 42 ==== SNAP ==== Let's have a look into the executable: $ objdump -d app.exe [...] 00000001004010d0 <main>: 1004010d0: 55 push %rbp 1004010d1: 48 89 e5 mov %rsp,%rbp 1004010d4: 48 83 ec 30 sub $0x30,%rsp 1004010d8: e8 93 00 00 00 callq 100401170 <__main> 1004010dd: b9 2a 00 00 00 mov $0x2a,%ecx 1004010e2: e8 59 06 00 00 callq 100401740 <foo> 1004010e7: 89 45 fc mov %eax,-0x4(%rbp) [...] So the call to foo is a call to address 1:00401740. Let's have a look what is at that address: 0000000100401740 <foo>: 100401740: ff 25 1a 5a 00 00 jmpq *0x5a1a(%rip) # 100407160 <__imp_foo> Address 100407160 is somewhere within the IAT which gets relocated at runtime. This is exactly as it's supposed to be. Now, here's the question: Where is your problem different? What exactly makes your code fail? Can you construct your problem from my simple testcase, or can you construct an equally simple testcase which fails? Corinna -- Corinna Vinschen Please, send mails regarding Cygwin to Cygwin Maintainer cygwin AT cygwin DOT com Red Hat [-- Attachment #2: Type: application/pgp-signature, Size: 819 bytes --] ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 8:43 ` Corinna Vinschen @ 2014-04-07 9:14 ` Jean-Pierre Flori 2014-04-07 9:39 ` Corinna Vinschen 2014-04-07 9:49 ` Jean-Pierre Flori 0 siblings, 2 replies; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-07 9:14 UTC (permalink / raw) To: cygwin Le Mon, 07 Apr 2014 10:43:12 +0200, Corinna Vinschen a écrit : > On Apr 6 20:20, Jean-Pierre Flori wrote: >> [...] >> The problem we recently encountered was the following: >> in gmp-impl.h, mpn_store (which can be either a macro or a function if >> efficient assembly is available, and so is always a function on x86_64) >> was not marked __declspec(dllexport/dllimport). >> (See https://github.com/wbhart/mpir/blob/master/gmp-impl.h#L2419 for >> the current version with the __GMP_DECLSPEC, defined in mpir.h (from >> gmp- h.in) where this gets defined as __declspec(dllimport) for the >> user visible header and use outside of MPIR itself) >> It seems that because of this lack, the call to mpn_store from a bunch >> of test executables produced the wrong callq instruction. >> Once we added the __GMP_DECLSPEC the function got correctly called. >> >> What I don't really get is that from what I've read e.g. here : >> https:// >> access.redhat.com/site/documentation/en-US/Red_Hat_Enterprise_Linux/4/ >> html/Using_ld_the_GNU_Linker/win32.html is that the dllimport/export >> should not be needed anymore. > > And in fact it isn't. > >> So I took a slightly deeper look and played with the definition of >> __GMP_DECLSPEC in gmp-h.in/mpir.h to be empty or __declspec(dllexport/ >> import). >> The library was built with: >> ./configure --disable-static --enable-shared make make check (-> >> potential segfaults when testing the mpn dir) >> >> As far as dllexport is concerned, we pass --export-all-symbols to ld, >> and as expected, we don't need the dllexport part when building the >> library (we get __imp_ and __nm_ symbols for functions). >> >> But it seems that the --enable-auto-import counterpart (which should be >> ld default) is defeated. >> I've had a look at the assembly and objects produced by gcc before >> linking and they indeed look different. >> With the dllimport magic, I get in t-neg.s: >> movq %rax, %rcx movq __imp___gmpn_store(%rip), %rax call >> *%rax >> Without it I get: >> movq %rax, %rcx call __gmpn_store >> Similar differences in the object file (t-neg.o). >> Looking at the exes produced (.libs/t-neg.exe) gives with the dllimport >> magic: >> 100401115: 48 89 c1 mov %rax,%rcx 100401118: >> 48 8b 05 f1 71 00 00 mov 0x71f1(%rip),%rax # >> 100408310 <__imp___gmpn_store> >> 10040111f: ff d0 callq *%rax >> Without it: >> 100401111: 48 89 c1 mov %rax,%rcx 100401114: >> e8 f7 71 00 00 callq 100408310 >> <__imp___gmpn_store> > > This is ok. Look closely at the address after the callq. It's the > start address of the executable (0x1:00400000) plus an offset. If you > disassemble the executable you will find a jmp statement at this > address. This is the trampoline code which is automatically generated > for external references if they are not marked with dllimport. > > The problem at this point is that I can't reproduce your issue with a > simple example. Here's the example: > > ==== SNIP ==== > $ cat > lib.c <<EOF #include <stdio.h> > > int foo (int a) > { > printf ("a = %d\n", a); > return a; > } > EOF $ cat > app.c <<EOF #include <stdio.h> > > extern int foo (int); > > int main () > { > int x = foo (42); printf ("x = %d\n", x); > return 0; > } > EOF $ gcc -g -shared -o lib.dll lib.c $ gcc -g -o app app.c lib.dll $ > ./app a = 42 x = 42 ==== SNAP ==== > > Let's have a look into the executable: > > $ objdump -d app.exe [...] > 00000001004010d0 <main>: > 1004010d0: 55 push %rbp 1004010d1: 48 89 > e5 mov %rsp,%rbp 1004010d4: 48 83 ec 30 > sub $0x30,%rsp 1004010d8: e8 93 00 00 00 callq > 100401170 <__main> > 1004010dd: b9 2a 00 00 00 mov $0x2a,%ecx 1004010e2: > e8 59 06 00 00 callq 100401740 <foo> > 1004010e7: 89 45 fc mov %eax,-0x4(%rbp) > [...] > > So the call to foo is a call to address 1:00401740. Let's have a look > what is at that address: > > 0000000100401740 <foo>: > 100401740: ff 25 1a 5a 00 00 jmpq *0x5a1a(%rip) # > 100407160 <__imp_foo> > > Address 100407160 is somewhere within the IAT which gets relocated at > runtime. For most functions I indeed see this trampoline trick within the binary. > > This is exactly as it's supposed to be. > > Now, here's the question: Where is your problem different? What > exactly makes your code fail? Can you construct your problem from my > simple testcase, or can you construct an equally simple testcase which > fails? Looking a little further, it seems the problematic functions are those directly assembled from assembly code. That was the case of mpn_store on x86_64. And when I remove all dllimport, the call to the function mpn_addadd_n also gives a segfault when executing t-addadd_n.exe. Note that the test t-aors.exe does not segfault, and indeed it only uses the mpn_add_1 and mpn_sub_1 functions which are not from assembly. I'll now try to produce a minimal example. (I've tried GCC 4.7.3 and it gives the same result.) Best, JP -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 9:14 ` Jean-Pierre Flori @ 2014-04-07 9:39 ` Corinna Vinschen 2014-04-07 9:55 ` Jean-Pierre Flori 2014-04-07 9:49 ` Jean-Pierre Flori 1 sibling, 1 reply; 21+ messages in thread From: Corinna Vinschen @ 2014-04-07 9:39 UTC (permalink / raw) To: cygwin [-- Attachment #1: Type: text/plain, Size: 4112 bytes --] On Apr 7 09:14, Jean-Pierre Flori wrote: > Le Mon, 07 Apr 2014 10:43:12 +0200, Corinna Vinschen a écrit : > > On Apr 6 20:20, Jean-Pierre Flori wrote: > >> Looking at the exes produced (.libs/t-neg.exe) gives with the dllimport > >> magic: > >> 100401115: 48 89 c1 mov %rax,%rcx 100401118: > >> 48 8b 05 f1 71 00 00 mov 0x71f1(%rip),%rax # > >> 100408310 <__imp___gmpn_store> > >> 10040111f: ff d0 callq *%rax > >> Without it: > >> 100401111: 48 89 c1 mov %rax,%rcx 100401114: > >> e8 f7 71 00 00 callq 100408310 > >> <__imp___gmpn_store> > > > > This is ok. Look closely at the address after the callq. It's the > > start address of the executable (0x1:00400000) plus an offset. If you > > disassemble the executable you will find a jmp statement at this > > address. This is the trampoline code which is automatically generated > > for external references if they are not marked with dllimport. > > > > The problem at this point is that I can't reproduce your issue with a > > simple example. Here's the example: > > > > ==== SNIP ==== > > $ cat > lib.c <<EOF #include <stdio.h> > > > > int foo (int a) > > { > > printf ("a = %d\n", a); > > return a; > > } > > EOF $ cat > app.c <<EOF #include <stdio.h> > > > > extern int foo (int); > > > > int main () > > { > > int x = foo (42); printf ("x = %d\n", x); > > return 0; > > } > > EOF $ gcc -g -shared -o lib.dll lib.c $ gcc -g -o app app.c lib.dll $ > > ./app a = 42 x = 42 ==== SNAP ==== > > > > Let's have a look into the executable: > > > > $ objdump -d app.exe [...] > > 00000001004010d0 <main>: > > 1004010d0: 55 push %rbp 1004010d1: 48 89 > > e5 mov %rsp,%rbp 1004010d4: 48 83 ec 30 > > sub $0x30,%rsp 1004010d8: e8 93 00 00 00 callq > > 100401170 <__main> > > 1004010dd: b9 2a 00 00 00 mov $0x2a,%ecx 1004010e2: > > e8 59 06 00 00 callq 100401740 <foo> > > 1004010e7: 89 45 fc mov %eax,-0x4(%rbp) > > [...] > > > > So the call to foo is a call to address 1:00401740. Let's have a look > > what is at that address: > > > > 0000000100401740 <foo>: > > 100401740: ff 25 1a 5a 00 00 jmpq *0x5a1a(%rip) # > > 100407160 <__imp_foo> > > > > Address 100407160 is somewhere within the IAT which gets relocated at > > runtime. > For most functions I indeed see this trampoline trick within the binary. > > > > This is exactly as it's supposed to be. > > > > Now, here's the question: Where is your problem different? What > > exactly makes your code fail? Can you construct your problem from my > > simple testcase, or can you construct an equally simple testcase which > > fails? > Looking a little further, it seems the problematic functions are those > directly assembled from assembly code. > That was the case of mpn_store on x86_64. Just for clarity: mpn_store is an assembler function calling an external C function, right? So IIUC, the assembler code in mpn_store contains a fixed callq, like this: callq foo And this crashes when foo is in an external DLL. This is no wonder at all. x86_64 does not have a callq opcode with 64 bit absolute addressing. What you get in the example above is 32 bit PC-relative addressing, so if foo is not part of the same binary, you're likely to crash because the offset is just wrong. AFAICS, what you have to do is to change your asse4mbler code to create your own jump trampoline, or any other method which evaluates the correct 64 bit address in a place which is accessible via callq: movq __imp_foo, %rax callq *%rax [...] __imp_foo: .quad foo or callq __jmp_foo [...] __jmp_foo jmp foo HTH, Corinna -- Corinna Vinschen Please, send mails regarding Cygwin to Cygwin Maintainer cygwin AT cygwin DOT com Red Hat [-- Attachment #2: Type: application/pgp-signature, Size: 819 bytes --] ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 9:39 ` Corinna Vinschen @ 2014-04-07 9:55 ` Jean-Pierre Flori 0 siblings, 0 replies; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-07 9:55 UTC (permalink / raw) To: cygwin Le Mon, 07 Apr 2014 11:39:32 +0200, Corinna Vinschen a écrit : > On Apr 7 09:14, Jean-Pierre Flori wrote: >> Le Mon, 07 Apr 2014 10:43:12 +0200, Corinna Vinschen a écrit : >> > On Apr 6 20:20, Jean-Pierre Flori wrote: >> >> Looking at the exes produced (.libs/t-neg.exe) gives with the >> >> dllimport magic: >> >> 100401115: 48 89 c1 mov %rax,%rcx 100401118: >> >> 48 8b 05 f1 71 00 00 mov 0x71f1(%rip),%rax # >> >> 100408310 <__imp___gmpn_store> >> >> 10040111f: ff d0 callq *%rax >> >> Without it: >> >> 100401111: 48 89 c1 mov %rax,%rcx 100401114: >> >> e8 f7 71 00 00 callq 100408310 >> >> <__imp___gmpn_store> >> > >> > This is ok. Look closely at the address after the callq. It's the >> > start address of the executable (0x1:00400000) plus an offset. If >> > you disassemble the executable you will find a jmp statement at this >> > address. This is the trampoline code which is automatically >> > generated for external references if they are not marked with >> > dllimport. >> > >> > The problem at this point is that I can't reproduce your issue with a >> > simple example. Here's the example: >> > >> > ==== SNIP ==== >> > $ cat > lib.c <<EOF #include <stdio.h> >> > >> > int foo (int a) >> > { >> > printf ("a = %d\n", a); >> > return a; >> > } >> > EOF $ cat > app.c <<EOF #include <stdio.h> >> > >> > extern int foo (int); >> > >> > int main () >> > { >> > int x = foo (42); printf ("x = %d\n", x); >> > return 0; >> > } >> > EOF $ gcc -g -shared -o lib.dll lib.c $ gcc -g -o app app.c lib.dll $ >> > ./app a = 42 x = 42 ==== SNAP ==== >> > >> > Let's have a look into the executable: >> > >> > $ objdump -d app.exe [...] >> > 00000001004010d0 <main>: >> > 1004010d0: 55 push %rbp 1004010d1: 48 >> > 89 e5 mov %rsp,%rbp 1004010d4: 48 83 ec 30 >> > sub $0x30,%rsp 1004010d8: e8 93 00 00 00 callq >> > 100401170 <__main> >> > 1004010dd: b9 2a 00 00 00 mov $0x2a,%ecx 1004010e2: >> > e8 59 06 00 00 callq 100401740 <foo> >> > 1004010e7: 89 45 fc mov %eax,-0x4(%rbp) >> > [...] >> > >> > So the call to foo is a call to address 1:00401740. Let's have a >> > look what is at that address: >> > >> > 0000000100401740 <foo>: >> > 100401740: ff 25 1a 5a 00 00 jmpq *0x5a1a(%rip) # >> > 100407160 <__imp_foo> >> > >> > Address 100407160 is somewhere within the IAT which gets relocated at >> > runtime. >> For most functions I indeed see this trampoline trick within the >> binary. >> > >> > This is exactly as it's supposed to be. >> > >> > Now, here's the question: Where is your problem different? What >> > exactly makes your code fail? Can you construct your problem from my >> > simple testcase, or can you construct an equally simple testcase >> > which fails? >> Looking a little further, it seems the problematic functions are those >> directly assembled from assembly code. >> That was the case of mpn_store on x86_64. > > Just for clarity: mpn_store is an assembler function calling an > external C function, right? > Nope, mpn_store is an assembler function indeed, but it's the call to this function which fails (which a callq which indeed seems to call it from the external library but that code was generated by gcc). -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 9:14 ` Jean-Pierre Flori 2014-04-07 9:39 ` Corinna Vinschen @ 2014-04-07 9:49 ` Jean-Pierre Flori 2014-04-07 10:42 ` Jean-Pierre Flori 1 sibling, 1 reply; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-07 9:49 UTC (permalink / raw) To: cygwin Le Mon, 07 Apr 2014 09:14:41 +0000, Jean-Pierre Flori a écrit : > Looking a little further, it seems the problematic functions are those > directly assembled from assembly code. > That was the case of mpn_store on x86_64. > > And when I remove all dllimport, the call to the function mpn_addadd_n > also gives a segfault when executing t-addadd_n.exe. > > Note that the test t-aors.exe does not segfault, and indeed it only uses > the mpn_add_1 and mpn_sub_1 functions which are not from assembly. > It seems the dll produced at least has different treatment for these tow kinds of functions. jp@napoleon-7 ~ $ nm local/bin/cygmpir-16.dll | grep store 00000004ff238170 T __gmpn_store 00000004ff238198 t __gmpn_store.1 00000004ff2381a0 t __gmpn_store.2 00000004ff2381b3 t __gmpn_store.3 00000004ff2381bd t __gmpn_store.4 00000004ff2381be t __gmpn_store.5 00000004ff2381c3 t __gmpn_store.6 00000004ff2381c9 t __gmpn_store.7 ... jp@napoleon-7 ~ $ nm local/bin/cygmpir-16.dll | grep addadd_n 00000004ff208e10 T __gmpn_addadd_n 00000004ff208e50 t __gmpn_addadd_n.1 00000004ff208eac t __gmpn_addadd_n.2 00000004ff208ebe t __gmpn_addadd_n.3 00000004ff208f0f t __gmpn_addadd_n.4 00000004ff208f54 t __gmpn_addadd_n.5 00000004ff208f6e t __gmpn_addadd_n.6 jp@napoleon-7 ~ $ nm local/bin/cygmpir-16.dll | grep add_1 00000004ff207d40 T __gmpn_add_1 And jp@napoleon-7 ~/mpir $ nm .libs/libmpir.dll.a | grep add_1 0000000000000000 T __gmpn_add_1 0000000000000000 I __imp___gmpn_add_1 jp@napoleon-7 ~/mpir $ nm .libs/libmpir.dll.a | grep addadd_n 0000000000000000 I __imp___gmpn_addadd_n 0000000000000000 I __nm___gmpn_addadd_n -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 9:49 ` Jean-Pierre Flori @ 2014-04-07 10:42 ` Jean-Pierre Flori 2014-04-07 10:45 ` Jean-Pierre Flori 0 siblings, 1 reply; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-07 10:42 UTC (permalink / raw) To: cygwin Le Mon, 07 Apr 2014 09:49:27 +0000, Jean-Pierre Flori a écrit : > Le Mon, 07 Apr 2014 09:14:41 +0000, Jean-Pierre Flori a écrit : >> Looking a little further, it seems the problematic functions are those >> directly assembled from assembly code. >> That was the case of mpn_store on x86_64. >> >> And when I remove all dllimport, the call to the function mpn_addadd_n >> also gives a segfault when executing t-addadd_n.exe. >> >> Note that the test t-aors.exe does not segfault, and indeed it only >> uses the mpn_add_1 and mpn_sub_1 functions which are not from assembly. >> > It seems the dll produced at least has different treatment for these tow > kinds of functions. > > jp@napoleon-7 ~ > $ nm local/bin/cygmpir-16.dll | grep store 00000004ff238170 T > __gmpn_store 00000004ff238198 t __gmpn_store.1 00000004ff2381a0 t > __gmpn_store.2 00000004ff2381b3 t __gmpn_store.3 00000004ff2381bd t > __gmpn_store.4 00000004ff2381be t __gmpn_store.5 00000004ff2381c3 t > __gmpn_store.6 00000004ff2381c9 t __gmpn_store.7 ... > > jp@napoleon-7 ~ > $ nm local/bin/cygmpir-16.dll | grep addadd_n 00000004ff208e10 T > __gmpn_addadd_n 00000004ff208e50 t __gmpn_addadd_n.1 00000004ff208eac t > __gmpn_addadd_n.2 00000004ff208ebe t __gmpn_addadd_n.3 00000004ff208f0f > t __gmpn_addadd_n.4 00000004ff208f54 t __gmpn_addadd_n.5 > 00000004ff208f6e t __gmpn_addadd_n.6 > > jp@napoleon-7 ~ > $ nm local/bin/cygmpir-16.dll | grep add_1 00000004ff207d40 T > __gmpn_add_1 > > And > > jp@napoleon-7 ~/mpir $ nm .libs/libmpir.dll.a | grep add_1 > 0000000000000000 T __gmpn_add_1 0000000000000000 I __imp___gmpn_add_1 > > jp@napoleon-7 ~/mpir $ nm .libs/libmpir.dll.a | grep addadd_n > 0000000000000000 I __imp___gmpn_addadd_n 0000000000000000 I > __nm___gmpn_addadd_n Note in particular the __nm_ prefix. It is as advertiserd here: http://www.cygwin.com/ml/cygwin/2002-01/ msg00236.html But when looking at the Cygwin32 produced import lib, I don't see any nm prefix. -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 10:42 ` Jean-Pierre Flori @ 2014-04-07 10:45 ` Jean-Pierre Flori 2014-04-07 11:26 ` Jean-Pierre Flori 0 siblings, 1 reply; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-07 10:45 UTC (permalink / raw) To: cygwin Le Mon, 07 Apr 2014 10:42:13 +0000, Jean-Pierre Flori a écrit : > Le Mon, 07 Apr 2014 09:49:27 +0000, Jean-Pierre Flori a écrit : > >> Le Mon, 07 Apr 2014 09:14:41 +0000, Jean-Pierre Flori a écrit : >>> Looking a little further, it seems the problematic functions are those >>> directly assembled from assembly code. >>> That was the case of mpn_store on x86_64. >>> >>> And when I remove all dllimport, the call to the function mpn_addadd_n >>> also gives a segfault when executing t-addadd_n.exe. >>> >>> Note that the test t-aors.exe does not segfault, and indeed it only >>> uses the mpn_add_1 and mpn_sub_1 functions which are not from >>> assembly. >>> >> It seems the dll produced at least has different treatment for these >> tow kinds of functions. >> >> jp@napoleon-7 ~ >> $ nm local/bin/cygmpir-16.dll | grep store 00000004ff238170 T >> __gmpn_store 00000004ff238198 t __gmpn_store.1 00000004ff2381a0 t >> __gmpn_store.2 00000004ff2381b3 t __gmpn_store.3 00000004ff2381bd t >> __gmpn_store.4 00000004ff2381be t __gmpn_store.5 00000004ff2381c3 t >> __gmpn_store.6 00000004ff2381c9 t __gmpn_store.7 ... >> >> jp@napoleon-7 ~ >> $ nm local/bin/cygmpir-16.dll | grep addadd_n 00000004ff208e10 T >> __gmpn_addadd_n 00000004ff208e50 t __gmpn_addadd_n.1 00000004ff208eac t >> __gmpn_addadd_n.2 00000004ff208ebe t __gmpn_addadd_n.3 00000004ff208f0f >> t __gmpn_addadd_n.4 00000004ff208f54 t __gmpn_addadd_n.5 >> 00000004ff208f6e t __gmpn_addadd_n.6 >> >> jp@napoleon-7 ~ >> $ nm local/bin/cygmpir-16.dll | grep add_1 00000004ff207d40 T >> __gmpn_add_1 >> >> And >> >> jp@napoleon-7 ~/mpir $ nm .libs/libmpir.dll.a | grep add_1 >> 0000000000000000 T __gmpn_add_1 0000000000000000 I __imp___gmpn_add_1 >> >> jp@napoleon-7 ~/mpir $ nm .libs/libmpir.dll.a | grep addadd_n >> 0000000000000000 I __imp___gmpn_addadd_n 0000000000000000 I >> __nm___gmpn_addadd_n > > Note in particular the __nm_ prefix. > It is as advertiserd here: http://www.cygwin.com/ml/cygwin/2002-01/ > msg00236.html But when looking at the Cygwin32 produced import lib, I > don't see any nm prefix. In fact, I see some... but for much fewer functions, strange. -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 10:45 ` Jean-Pierre Flori @ 2014-04-07 11:26 ` Jean-Pierre Flori 2014-04-07 11:30 ` Corinna Vinschen 0 siblings, 1 reply; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-07 11:26 UTC (permalink / raw) To: cygwin Le Mon, 07 Apr 2014 10:43:30 +0000, Jean-Pierre Flori a écrit : >> >> Note in particular the __nm_ prefix. >> It is as advertiserd here: http://www.cygwin.com/ml/cygwin/2002-01/ >> msg00236.html But when looking at the Cygwin32 produced import lib, I >> don't see any nm prefix. > > In fact, I see some... but for much fewer functions, strange. I have troubles understanding when this _nm_ prefix actually gets added, any help welcome :) Is there any dark magic related to inlining? -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 11:26 ` Jean-Pierre Flori @ 2014-04-07 11:30 ` Corinna Vinschen 2014-04-07 11:50 ` Jean-Pierre Flori 0 siblings, 1 reply; 21+ messages in thread From: Corinna Vinschen @ 2014-04-07 11:30 UTC (permalink / raw) To: cygwin [-- Attachment #1: Type: text/plain, Size: 960 bytes --] On Apr 7 11:26, Jean-Pierre Flori wrote: > Le Mon, 07 Apr 2014 10:43:30 +0000, Jean-Pierre Flori a écrit : > >> > >> Note in particular the __nm_ prefix. > >> It is as advertiserd here: http://www.cygwin.com/ml/cygwin/2002-01/ > >> msg00236.html But when looking at the Cygwin32 produced import lib, I > >> don't see any nm prefix. > > > > In fact, I see some... but for much fewer functions, strange. > > I have troubles understanding when this _nm_ prefix actually gets added, > any help welcome :) > Is there any dark magic related to inlining? I'm sorry, but I don't know how this works exactly. The nm prefix is only added for external references, not for inlined functions, but I don't know the gory details. You may be better off to ask on the gcc mailing list. Corinna -- Corinna Vinschen Please, send mails regarding Cygwin to Cygwin Maintainer cygwin AT cygwin DOT com Red Hat [-- Attachment #2: Type: application/pgp-signature, Size: 819 bytes --] ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 11:30 ` Corinna Vinschen @ 2014-04-07 11:50 ` Jean-Pierre Flori 2014-04-07 11:57 ` Corinna Vinschen 0 siblings, 1 reply; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-07 11:50 UTC (permalink / raw) To: cygwin Le Mon, 07 Apr 2014 13:30:27 +0200, Corinna Vinschen a écrit : > > I'm sorry, but I don't know how this works exactly. The nm prefix is > only added for external references, not for inlined functions, but I > don't know the gory details. You may be better off to ask on the gcc > mailing list. > No problem, I've already learned tons of stuff thanks to your help. I've just posted on gcc-help. http://gcc.gnu.org/ml/gcc-help/2014-04/msg00024.html -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 11:50 ` Jean-Pierre Flori @ 2014-04-07 11:57 ` Corinna Vinschen 2014-04-07 13:28 ` Jean-Pierre Flori 0 siblings, 1 reply; 21+ messages in thread From: Corinna Vinschen @ 2014-04-07 11:57 UTC (permalink / raw) To: cygwin [-- Attachment #1: Type: text/plain, Size: 751 bytes --] On Apr 7 11:50, Jean-Pierre Flori wrote: > Le Mon, 07 Apr 2014 13:30:27 +0200, Corinna Vinschen a écrit : > > > > I'm sorry, but I don't know how this works exactly. The nm prefix is > > only added for external references, not for inlined functions, but I > > don't know the gory details. You may be better off to ask on the gcc > > mailing list. > > > No problem, I've already learned tons of stuff thanks to your help. > I've just posted on gcc-help. > http://gcc.gnu.org/ml/gcc-help/2014-04/msg00024.html Thanks. A simple testcase would still be nice, of course. Corinna -- Corinna Vinschen Please, send mails regarding Cygwin to Cygwin Maintainer cygwin AT cygwin DOT com Red Hat [-- Attachment #2: Type: application/pgp-signature, Size: 819 bytes --] ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 11:57 ` Corinna Vinschen @ 2014-04-07 13:28 ` Jean-Pierre Flori 2014-04-07 14:03 ` Jean-Pierre Flori 0 siblings, 1 reply; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-07 13:28 UTC (permalink / raw) To: cygwin Le Mon, 07 Apr 2014 13:57:30 +0200, Corinna Vinschen a écrit : > On Apr 7 11:50, Jean-Pierre Flori wrote: >> Le Mon, 07 Apr 2014 13:30:27 +0200, Corinna Vinschen a écrit : >> > >> > I'm sorry, but I don't know how this works exactly. The nm prefix is >> > only added for external references, not for inlined functions, but I >> > don't know the gory details. You may be better off to ask on the gcc >> > mailing list. >> > >> No problem, I've already learned tons of stuff thanks to your help. >> I've just posted on gcc-help. >> http://gcc.gnu.org/ml/gcc-help/2014-04/msg00024.html > > Thanks. A simple testcase would still be nice, of course. > > Sure, but it seems the issue is that I cannot get the __nm_ prefix when I elaborate on a minimal problem like you did. I'll still try to get something this afternoon. -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 13:28 ` Jean-Pierre Flori @ 2014-04-07 14:03 ` Jean-Pierre Flori 2014-04-07 14:36 ` Corinna Vinschen 0 siblings, 1 reply; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-07 14:03 UTC (permalink / raw) To: cygwin Le Mon, 07 Apr 2014 13:28:19 +0000, Jean-Pierre Flori a écrit : > Le Mon, 07 Apr 2014 13:57:30 +0200, Corinna Vinschen a écrit : > >> On Apr 7 11:50, Jean-Pierre Flori wrote: >>> Le Mon, 07 Apr 2014 13:30:27 +0200, Corinna Vinschen a écrit : >>> > >>> > I'm sorry, but I don't know how this works exactly. The nm prefix >>> > is only added for external references, not for inlined functions, >>> > but I don't know the gory details. You may be better off to ask on >>> > the gcc mailing list. >>> > >>> No problem, I've already learned tons of stuff thanks to your help. >>> I've just posted on gcc-help. >>> http://gcc.gnu.org/ml/gcc-help/2014-04/msg00024.html >> >> Thanks. A simple testcase would still be nice, of course. >> >> > Sure, but it seems the issue is that I cannot get the __nm_ prefix when > I elaborate on a minimal problem like you did. > > I'll still try to get something this afternoon. I think I got something: $ cat > lib.c <<EOF #include <stdio.h> int foo (int a) { printf ("a = %d\n", a); return a; } EOF $cat > asm.as <<EOF global nothing ;export nothing nothing: ret end EOF $ cat > app.c <<EOF #include <stdio.h> extern int foo (int); int main () { int x = foo (42); printf ("x = %d\n", x); nothing(); return 0; } EOF $ gcc -g -c lib.c -o lib.o $ yasm -fx64 asm.as -o asm.o $ gcc -shared lib.o ams.o -Wl,--out-implib=lib.dll.a -Wl,--export-all- symbols -o lib.dll $ gcc -g -o app app.c -L. -llib $ ./app ... <segfault> Without the export directive (commented above) I get __nm_ prefix and wrong callq instruction. With it, the __nm_prefix disappears and the trampoline correctly used. -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 14:03 ` Jean-Pierre Flori @ 2014-04-07 14:36 ` Corinna Vinschen 2014-04-07 14:48 ` Jean-Pierre Flori 0 siblings, 1 reply; 21+ messages in thread From: Corinna Vinschen @ 2014-04-07 14:36 UTC (permalink / raw) To: cygwin [-- Attachment #1: Type: text/plain, Size: 3347 bytes --] On Apr 7 14:02, Jean-Pierre Flori wrote: > Le Mon, 07 Apr 2014 13:28:19 +0000, Jean-Pierre Flori a écrit : > > > Le Mon, 07 Apr 2014 13:57:30 +0200, Corinna Vinschen a écrit : > > > >> On Apr 7 11:50, Jean-Pierre Flori wrote: > >>> Le Mon, 07 Apr 2014 13:30:27 +0200, Corinna Vinschen a écrit : > >>> > > >>> > I'm sorry, but I don't know how this works exactly. The nm prefix > >>> > is only added for external references, not for inlined functions, > >>> > but I don't know the gory details. You may be better off to ask on > >>> > the gcc mailing list. > >>> > > >>> No problem, I've already learned tons of stuff thanks to your help. > >>> I've just posted on gcc-help. > >>> http://gcc.gnu.org/ml/gcc-help/2014-04/msg00024.html > >> > >> Thanks. A simple testcase would still be nice, of course. > >> > >> > > Sure, but it seems the issue is that I cannot get the __nm_ prefix when > > I elaborate on a minimal problem like you did. > > > > I'll still try to get something this afternoon. > I think I got something: > $ cat > lib.c <<EOF > #include <stdio.h> > > int > foo (int a) > { > printf ("a = %d\n", a); > return a; > } > EOF > $cat > asm.as <<EOF > global nothing > ;export nothing > nothing: > ret > end > EOF > $ cat > app.c <<EOF > #include <stdio.h> > > extern int foo (int); > > int > main () > { > int x = foo (42); > printf ("x = %d\n", x); > nothing(); > return 0; > } > EOF > $ gcc -g -c lib.c -o lib.o > $ yasm -fx64 asm.as -o asm.o > $ gcc -shared lib.o ams.o -Wl,--out-implib=lib.dll.a -Wl,--export-all- > symbols -o lib.dll > $ gcc -g -o app app.c -L. -llib > $ ./app > ... > <segfault> > > Without the export directive (commented above) I get __nm_ prefix and > wrong callq instruction. > With it, the __nm_prefix disappears and the trampoline correctly used. I think you must define the export (gas: .def) pseudo op when creating your own assembler code exporting a symbol from a DLL. If you look into the code created by gcc from lib.c: $ gcc -S lib.c $ cat lib.s .file "lib.c" .section .rdata,"dr" .LC0: .ascii "a = %d\12\0" .text .globl foo .def foo; .scl 2; .type 32; .endef .seh_proc foo foo: pushq %rbp .seh_pushreg %rbp movq %rsp, %rbp .seh_setframe %rbp, 0 subq $32, %rsp .seh_stackalloc 32 .seh_endprologue movl %ecx, 16(%rbp) movl 16(%rbp), %edx leaq .LC0(%rip), %rcx call printf movl 16(%rbp), %eax addq $32, %rsp popq %rbp ret .seh_endproc .ident "GCC: (GNU) 4.8.2" .def printf; .scl 2; .type 32; .endef At this point gcc doesn't know that foo will get exported from a DLL, but it generates the .def directive nevertheless. If I create the same code in gas: .text .globl nothing .def nothing; .scl 2; .type 32; .endef nothing: ret then it works, but crashes if I omit the .def directive. So it seems to me you don't have to export the symbol using the dllimport/dllexport directives, but you have to specify the symbol explicitely for export. Corinna [-- Attachment #2: Type: application/pgp-signature, Size: 819 bytes --] ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 14:36 ` Corinna Vinschen @ 2014-04-07 14:48 ` Jean-Pierre Flori 2014-04-07 15:39 ` Corinna Vinschen 0 siblings, 1 reply; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-07 14:48 UTC (permalink / raw) To: cygwin Le Mon, 07 Apr 2014 16:36:18 +0200, Corinna Vinschen a écrit : > On Apr 7 14:02, Jean-Pierre Flori wrote: >> Le Mon, 07 Apr 2014 13:28:19 +0000, Jean-Pierre Flori a écrit : >> >> > Le Mon, 07 Apr 2014 13:57:30 +0200, Corinna Vinschen a écrit : >> > >> >> On Apr 7 11:50, Jean-Pierre Flori wrote: >> >>> Le Mon, 07 Apr 2014 13:30:27 +0200, Corinna Vinschen a écrit : >> >>> > >> >>> > I'm sorry, but I don't know how this works exactly. The nm >> >>> > prefix is only added for external references, not for inlined >> >>> > functions, but I don't know the gory details. You may be better >> >>> > off to ask on the gcc mailing list. >> >>> > >> >>> No problem, I've already learned tons of stuff thanks to your help. >> >>> I've just posted on gcc-help. >> >>> http://gcc.gnu.org/ml/gcc-help/2014-04/msg00024.html >> >> >> >> Thanks. A simple testcase would still be nice, of course. >> >> >> >> >> > Sure, but it seems the issue is that I cannot get the __nm_ prefix >> > when I elaborate on a minimal problem like you did. >> > >> > I'll still try to get something this afternoon. >> I think I got something: >> $ cat > lib.c <<EOF #include <stdio.h> >> >> int foo (int a) >> { >> printf ("a = %d\n", a); >> return a; >> } >> EOF $cat > asm.as <<EOF global nothing ;export nothing nothing: >> ret end >> EOF $ cat > app.c <<EOF #include <stdio.h> >> >> extern int foo (int); >> >> int main () >> { >> int x = foo (42); printf ("x = %d\n", x); >> nothing(); >> return 0; >> } >> EOF $ gcc -g -c lib.c -o lib.o $ yasm -fx64 asm.as -o asm.o $ gcc >> -shared lib.o ams.o -Wl,--out-implib=lib.dll.a -Wl,--export-all- >> symbols -o lib.dll $ gcc -g -o app app.c -L. -llib $ ./app ... >> <segfault> >> >> Without the export directive (commented above) I get __nm_ prefix and >> wrong callq instruction. >> With it, the __nm_prefix disappears and the trampoline correctly used. > > I think you must define the export (gas: .def) pseudo op when creating > your own assembler code exporting a symbol from a DLL. If you look into > the code created by gcc from lib.c: > > $ gcc -S lib.c $ cat lib.s > .file "lib.c" > .section .rdata,"dr" > .LC0: > .ascii "a = %d\12\0" > .text .globl foo .def foo; .scl 2; .type 32; > .endef .seh_proc foo > foo: > pushq %rbp .seh_pushreg %rbp movq %rsp, %rbp > .seh_setframe %rbp, 0 subq $32, %rsp .seh_stackalloc 32 > .seh_endprologue movl %ecx, 16(%rbp) > movl 16(%rbp), %edx leaq .LC0(%rip), %rcx call printf > movl 16(%rbp), %eax addq $32, %rsp popq %rbp ret > .seh_endproc .ident "GCC: (GNU) 4.8.2" > .def printf; .scl 2; .type 32; .endef > > At this point gcc doesn't know that foo will get exported from a DLL, > but it generates the .def directive nevertheless. If I create the same > code in gas: > > .text .globl nothing .def nothing; .scl 2; .type 32; .endef > nothing: > ret > > then it works, but crashes if I omit the .def directive. So it seems to > me you don't have to export the symbol using the dllimport/dllexport > directives, but you have to specify the symbol explicitely for export. > Exactly! I came to the same conclusion. On top of that, it seems that including the export stuff does not hurt when building and linking a static lib. What's strange is that when we use the dllimport magic then it works even though the symbol was not explicitely exported. Thanks for the support. JP -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-07 14:48 ` Jean-Pierre Flori @ 2014-04-07 15:39 ` Corinna Vinschen 0 siblings, 0 replies; 21+ messages in thread From: Corinna Vinschen @ 2014-04-07 15:39 UTC (permalink / raw) To: cygwin [-- Attachment #1: Type: text/plain, Size: 1272 bytes --] On Apr 7 14:47, Jean-Pierre Flori wrote: > Le Mon, 07 Apr 2014 16:36:18 +0200, Corinna Vinschen a écrit : > > At this point gcc doesn't know that foo will get exported from a DLL, > > but it generates the .def directive nevertheless. If I create the same > > code in gas: > > > > .text .globl nothing .def nothing; .scl 2; .type 32; .endef > > nothing: > > ret > > > > then it works, but crashes if I omit the .def directive. So it seems to > > me you don't have to export the symbol using the dllimport/dllexport > > directives, but you have to specify the symbol explicitely for export. > > > Exactly! > I came to the same conclusion. > On top of that, it seems that including the export stuff does not hurt > when building and linking a static lib. > > What's strange is that when we use the dllimport magic then it works even > though the symbol was not explicitely exported. Perhaps not. With dllimport, the calling code expects having to import a symbol from the DLL, so it generates an IAT entry and everything works as expected. Along these lines, at least. Corinna -- Corinna Vinschen Please, send mails regarding Cygwin to Cygwin Maintainer cygwin AT cygwin DOT com Red Hat [-- Attachment #2: Type: application/pgp-signature, Size: 819 bytes --] ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: Possibly wrong address passed to callq asm instruction within MPIR test binaries 2014-04-01 22:07 Possibly wrong address passed to callq asm instruction within MPIR test binaries Jean-Pierre Flori 2014-04-02 9:07 ` Corinna Vinschen @ 2014-04-03 13:02 ` Jean-Pierre Flori 1 sibling, 0 replies; 21+ messages in thread From: Jean-Pierre Flori @ 2014-04-03 13:02 UTC (permalink / raw) To: cygwin Le Wed, 02 Apr 2014 00:07:12 +0200, Jean-Pierre Flori a écrit : > Dear all, > > It's amazing to see how well Cygwin64 is going. > Thanks for your hard work. > > While preparing the new MPIR release, which will be the first one to > support Cygwin4, we encountered problems running MPIR testsuite when > MPIR was configured to produce a shared lib. > That's with latest cygwin/binutils/gcc/g++ from today. > > It seems that a call to the MPN_ZERO macro, which on my setup is at > 0x4ff2746c0 in the shared lib but we get the instruction: > callq 0xff2746c0 within the test binary and that yields a nice segfault. > Please see > https://groups.google.com/d/msg/mpir-devel/KzsxIWhVx8A/EAUoP4ybWOMJ and > the few following post for more details. > > For sure, we don't get what's going on here. > Would you have any clue? > Might ld decide for some reason to trim the macro address to 4 bytes > rather than 8? > > Best, Sorry for the noise, we found the issue. Apparently it was some DLL export/import issue... See https://groups.google.com/d/msg/mpir-devel/KzsxIWhVx8A/D6-Z5SsLdGsJ Best, JP -- Problem reports: http://cygwin.com/problems.html FAQ: http://cygwin.com/faq/ Documentation: http://cygwin.com/docs.html Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple ^ permalink raw reply [flat|nested] 21+ messages in thread
end of thread, other threads:[~2014-04-07 15:39 UTC | newest] Thread overview: 21+ messages (download: mbox.gz / follow: Atom feed) -- links below jump to the message on this page -- 2014-04-01 22:07 Possibly wrong address passed to callq asm instruction within MPIR test binaries Jean-Pierre Flori 2014-04-02 9:07 ` Corinna Vinschen 2014-04-06 20:20 ` Jean-Pierre Flori 2014-04-07 7:52 ` Achim Gratz 2014-04-07 8:43 ` Corinna Vinschen 2014-04-07 9:14 ` Jean-Pierre Flori 2014-04-07 9:39 ` Corinna Vinschen 2014-04-07 9:55 ` Jean-Pierre Flori 2014-04-07 9:49 ` Jean-Pierre Flori 2014-04-07 10:42 ` Jean-Pierre Flori 2014-04-07 10:45 ` Jean-Pierre Flori 2014-04-07 11:26 ` Jean-Pierre Flori 2014-04-07 11:30 ` Corinna Vinschen 2014-04-07 11:50 ` Jean-Pierre Flori 2014-04-07 11:57 ` Corinna Vinschen 2014-04-07 13:28 ` Jean-Pierre Flori 2014-04-07 14:03 ` Jean-Pierre Flori 2014-04-07 14:36 ` Corinna Vinschen 2014-04-07 14:48 ` Jean-Pierre Flori 2014-04-07 15:39 ` Corinna Vinschen 2014-04-03 13:02 ` Jean-Pierre Flori
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).