64-Bit Windows applications typically expect the Twain Data Source manager to be named twaindsm.dll.
Send the DG_CONTROL/DAT_ENTRYPOINT/MSG_SET before DG_CONTROL/DAT_IDENTITY/MSG_OPENDS so sane.ds does not need to know the module name to find the DSM entry point.
An explanation for the request to offer the name twaindsm.dll for 64-Bit windows is offered here by the TWAIN organization:
https://github.com/twain/twain-dsm/blob/master/TWAIN_DSM/src/readme.doc
They cannot update the twain_32.dll installed and maintained by Microsoft, so they choose the new name twaindsm.dll instead. This name is also used at least by Irfanview and oder versions oder LibreOffice (Newer Libreoffice version start a 32-Bit process for 32-Bit TWAIN usage).
This Merge request also changes the twain_32.dll so that it send it's entry points earlier, before opening the data source. This is the same behaviour as the twaindsm.dll from the TWAIN organization from [https://github.com/twain/twain-dsm/%5D(https://github.com/twain/twain-dsm/bl...)
Otherwise sane.ds would in MSG_OPENDS try to find the DSM entry point based on the module-name "twain_32" in sane_main.c:60:
``` if (SANE_dsmentry == NULL) { HMODULE moddsm = GetModuleHandleW(L"twain_32");
if (moddsm) SANE_dsmentry = (void*)GetProcAddress(moddsm, "DSM_Entry");
if (!SANE_dsmentry) { ERR("can't find DSM entry point\n"); return TWRC_FAILURE; } } ```
-- v2: dlls/twain_32: Offer TWAIN DSM as twaindsm.dll for 64 Bit and send DAT_ENTRYPOINT earlier.
From: Bernd Herd codeberg@herdsoft.com
64-Bit windows applications expect the Twain Data Source manager to be named twaindsm.dll.
Send the DG_CONTROL/DAT_ENTRYPOINT/MSG_SET before DG_CONTROL/DAT_IDENTITY/MSG_OPENDS so sane.ds does not need to know the module name to find the DSM entry point --- dlls/twain_32/dsm_ctrl.c | 32 +++++++++++++++++++++++--------- loader/wine.inf.in | 1 + 2 files changed, 24 insertions(+), 9 deletions(-)
diff --git a/dlls/twain_32/dsm_ctrl.c b/dlls/twain_32/dsm_ctrl.c index 89e788f979d..436654bfcc7 100644 --- a/dlls/twain_32/dsm_ctrl.c +++ b/dlls/twain_32/dsm_ctrl.c @@ -381,8 +381,31 @@ TW_UINT16 TWAIN_OpenDS (pTW_IDENTITY pOrigin, TW_MEMREF pData) } newSource->hmod = hmod; newSource->dsEntry = (DSENTRYPROC)GetProcAddress(hmod, "DS_Entry"); + if (!newSource->dsEntry) { + ERR("Failed to find DS_Entry() in TWAIN DS %s\n", debugstr_w(devices[i].modname)); + DSM_twCC = TWCC_OPERATIONERROR; + HeapFree(GetProcessHeap(), 0, newSource); + return TWRC_FAILURE; + } /* Assign id for the opened data source */ pIdentity->Id = DSM_sourceId ++; + /* Get the Identity of the new DS, so we know the SupportedGroups */ + if (TWRC_SUCCESS != newSource->dsEntry (NULL, DG_CONTROL, DAT_IDENTITY, MSG_GET, pIdentity)) { + DSM_twCC = TWCC_OPERATIONERROR; + HeapFree(GetProcessHeap(), 0, newSource); + DSM_sourceId--; + return TWRC_FAILURE; + } + /* Tell the source our entry points */ + if (pIdentity->SupportedGroups & DF_DS2) { + /* This makes sure that the DS knows the current address of our DSM_Entry + * function so there is no risk that it is using a stale copy. + * The other entry points are also set for formal reasons, + * but are currently not used. + */ + newSource->dsEntry (pOrigin, DG_CONTROL, DAT_ENTRYPOINT, MSG_SET, (TW_ENTRYPOINT *) &_entrypoints); + } + /* Open the data source */ if (TWRC_SUCCESS != newSource->dsEntry (pOrigin, DG_CONTROL, DAT_IDENTITY, MSG_OPENDS, pIdentity)) { DSM_twCC = TWCC_OPERATIONERROR; HeapFree(GetProcessHeap(), 0, newSource); @@ -399,15 +422,6 @@ TW_UINT16 TWAIN_OpenDS (pTW_IDENTITY pOrigin, TW_MEMREF pData) activeSources = newSource; DSM_twCC = TWCC_SUCCESS;
- /* Tell the source our entry points */ - if (pIdentity->SupportedGroups & DF_DS2) { - /* This makes sure that the DS knows the current address of our DSM_Entry - * function so there is no risk that it is using a stale copy. - * The other entry points are also set for formal reasons, - * but are currently not used. - */ - newSource->dsEntry (pOrigin, DG_CONTROL, DAT_ENTRYPOINT, MSG_SET, (TW_ENTRYPOINT *) &_entrypoints); - } return TWRC_SUCCESS; }
diff --git a/loader/wine.inf.in b/loader/wine.inf.in index 7dc657cc9e0..551af7883f7 100644 --- a/loader/wine.inf.in +++ b/loader/wine.inf.in @@ -731,6 +731,7 @@ HKLM,SOFTWARE\Microsoft\VisualStudio\14.0\VC\Runtimes\x86,"Version",2,"14.42.344 [FakeDllsWin64] 10,twain_64,sane.ds 10,twain_64,gphoto2.ds +11,,twaindsm.dll,twain_32.dll
; Wow64-only fake dlls [FakeDllsWow64]