问题
I can't login WINEHQ Bugzilla, so I ask here and this is the requirement:
We have a windows app which we have exe source code, and it used ATL. The dlls the exe depends require some special device, but mostly they have linux version. Now we need to port the windows app to linux.
My finally try: write a middle dll to wrap some lib which already is cross platform, the exe will call new middle dll, and I name the middle dll is "WINE custom build-in dll". CUSTOM means I compile this dll.so standalone by winemaker. Everything is fine until run it under wine64, the command line in linux shell:
wine64 portsome.exe
here is the output:
wine: Call from 0x7bc5eeec to unimplemented function wrapsome.dll.wrap_SOME_GetVersion, aborting
Backtrace:
=>0 0x000000007bc5eeec stub_entry_point+0x5c(dll=<is not available>, name=<is not available>, ret_addr=<is not available>) [/home/root0/src/wine/build/dlls/ntdll/../../../src/dlls/ntdll/loader.c:215] in ntdll (0x000000000023fbc0)
1 0x0000000140001022 in portsome (+0x1021) (0x000000000023fbc0)
2 0x00000001400012e2 in portsome (+0x12e1) (0x000000000023fd70)
3 0x000000007b47d02f start_process+0xbe(entry=0x140001418)
Modules:
Module Address Debug info Name (23 modules)
ELF 7b400000- 7b81a000 Dwarf kernel32<elf>
\-PE 7b420000- 7b81a000 \ kernel32
ELF 7bc00000- 7bd21000 Dwarf ntdll<elf>
\-PE 7bc20000- 7bd21000 \ ntdll
ELF 7c000000- 7c004000 Deferred <wine-loader>
PE 140000000- 140007000 Export portsome
ELF 7fbfe53b4000- 7fbfe56c6000 Deferred msvcr100<elf>
\-PE 7fbfe53e0000- 7fbfe56c6000 \ msvcr100
ELF 7fbfe5b48000- 7fbfe5f1d000 Deferred libhwaware.so
ELF 7fbfe5f1d000- 7fbfe6131000 Deferred wrapsome<elf>
\-PE 7fbfe5f20000- 7fbfe6131000 \ wrapsome
ELF 7fbfe66bc000- 7fbfe68ce000 Deferred libnss_files.so.2
ELF 7fbfe68ce000- 7fbfe6ada000 Deferred libnss_nis.so.2
ELF 7fbfe6ada000- 7fbfe6cf3000 Deferred libnsl.so.1
ELF 7fbfe6cf3000- 7fbfe6efc000 Deferred libnss_compat.so.2
ELF 7fbfe70fc000- 7fbfe7312000 Deferred libgcc_s.so.1
ELF 7fbfe7312000- 7fbfe761b000 Deferred libm.so.6
ELF 7fbfe761e000- 7fbfe7822000 Deferred libdl.so.2
ELF 7fbfe7822000- 7fbfe7bec000 Deferred libc.so.6
ELF 7fbfe7bed000- 7fbfe7e0a000 Deferred libpthread.so.0
ELF 7fbfe7e22000- 7fbfe81c8000 Dwarf libwine.so.1
ELF 7fbfe81ca000- 7fbfe83f2000 Deferred ld-linux-x86-64.so.2
ELF 7ffd8bbe1000- 7ffd8bbe2000 Deferred [vdso].so
Here is my question:
how do I compile a wine custom build-in dll to make windows native app can call its function when running, is it need to generate a fake dll by winebuilder?
Detail steps I working for port windows app to linux:
1. find the special dll which need contact with hardware directly, like CUDA, dongle access.
2. make a wrap dll, change the exe code to call this wrap dll function, and the wrap dll then call hardware aware dll.
3. create "wrapsome.spec" file with https://wiki.winehq.org/Winelib_User%27s_Guide#The_Spec_file requirements.
4. copy the wrap code to Ubuntu 16.04, switch to wrap code source directory and run below command in shell:
winemaker --dll --nosource-fix -DWRAPSOME_EXPORTS -I../deps/hdaware -L../deps/hdaware -lhdaware .
then I got the "Makefile" file and I append -fPIC to LDFLAGS.
5. continue to run "make", yea, I got the wrapsome.dll.so, and I copy it to wine build-in dlls directory.
6. finally I failed to run "wine64 portsome.exe", the question is mentioned above.
wine report "unimplemented function wrapsome.dll.wrap_SOME_GetVersion", I even confirmed with nm wrapsome.dll.so
, and here is its output:
0000000000213291 B __bss_start
0000000000213298 b call_fini.9485
0000000000213294 b completed.7585
w __cxa_finalize
00000000000118b0 t deregister_tm_clones
0000000000011a20 t DisableThreadLibraryCalls
0000000000011bf0 t DllMain
0000000000011940 t __do_global_dtors_aux
0000000000212de8 t __do_global_dtors_aux_fini_array_entry
0000000000213040 d __dso_handle
0000000000212df8 d _DYNAMIC
0000000000213291 D _edata
00000000002132a0 B _end
0000000000011c88 t _fini
0000000000011980 t frame_dummy
0000000000212de0 t __frame_dummy_init_array_entry
0000000000011ec8 r __FRAME_END__
0000000000213000 d _GLOBAL_OFFSET_TABLE_
w __gmon_start__
0000000000011cb8 r __GNU_EH_FRAME_HDR
0000000000000810 t _init
w _ITM_deregisterTMCloneTable
w _ITM_registerTMCloneTable
0000000000212df0 d __JCR_END__
0000000000212df0 d __JCR_LIST__
w _Jv_RegisterClasses
00000000000118f0 t register_tm_clones
U SOME_GetVersion
U SOME_InitAwareSDK
U SOME_UninitAwareSDK
0000000000213298 d __TMC_END__
U __wine_dll_register@@WINE_1.0
U __wine_main_argc@@WINE_1.0
U __wine_main_argv@@WINE_1.0
0000000000011ad0 t __wine_spec_dll_entry
0000000000011c94 r __wine_spec_file_name
0000000000011a20 t __wine_spec_import_thunks
0000000000011c20 t __wine_spec_init
0000000000011c40 t __wine_spec_init_ctor
000000000021329c b __wine_spec_init_state
0000000000213048 d __wine_spec_nt_header
000000000000082a t __wine_spec_pe_header
00000000000119b0 t __wine_spec_relay_entry_points
0000000000011ab9 T wrap_SOME_GetVersion
0000000000011a3c T wrap_SOME_InitAwareSDK
0000000000011a53 T wrap_SOME_UninitAwareSDK
0000000000011a26 T _Z7DllMainP11HINSTANCE__jPv
Notice: I have dismissed some word with common ones as it is not good to show to the public.
I even read the wine source code in github https://github.com/wine-mirror/wine/blob/fdac39f697e049ead215b164bfe6953269ffa7be/dlls/ntdll/loader.c#L660, it seemsexports = RtlImageDirectoryEntryToData( imp_mod, TRUE, IMAGE_DIRECTORY_ENTRY_EXPORT, &exp_size );
can't export the warpsome.dll.so file symbol table which I compile by winemaker+winegcc tool chain.
回答1:
I changed the wrapsome.spec file to this content:
@ stdcall wrap_SOME_InitAwareSDK(ptr) wrap_SOME_InitAwareSDK
@ stdcall wrap_SOME_UninitAwareSDK(ptr) wrap_SOME_UninitAwareSDK
@ stdcall wrap_SOME_GetVersion() wrap_SOME_GetVersion
and make again, then cp to wine dlls directory, it works! And I known there is no need to change the exe link to warp dll in windows, just build a dll.so with extract the same export name which need by exe, it should works too. I will try it later.
来源:https://stackoverflow.com/questions/46380191/wine-cant-load-my-custom-build-in-dll-and-report-call-to-unimplemented-functio