• ffidl to access dll functions

    From pd@21:1/5 to All on Fri Apr 15 17:20:43 2022
    I was trying to use ffidl to access functions defined in a dll located in the same folder of my tcl script.

    I'm using a windows machine executing the script both using cmd.exe and cygwin to execute "tclsh.exe myscript.tcl"

    Every attempt get the same error:

    couldn't load file "AutoItDLL.dll" : ???

    I've tried every combination of path to name the dll file, for example this:

    lappend auto_path [pwd]
    package require Ffidl
    set DLL AutoItDLL.dll
    set DLL [file nativename "[pwd]\\$DLL"]
    puts "$DLL"
    ffidl::callout AUTOIT_BlockInput {int} int [ffidl::symbol $DLL AUTOIT_BlockInput]

    c:\tcl> tclsh pp.tcl
    C:\tcl\AutoItDLL.dll
    couldn't load file "C:\tcl\AutoItDLL.dll" : ???
    while executing
    "ffidl::symbol $DLL AUTOIT_BlockInput"
    invoked from within
    "ffidl::callout AUTOIT_BlockInput {int} int [ffidl::symbol $DLL AUTOIT_BlockInput]"
    (file "pp.tcl" line 9)

    If I use a system dll like user32.dll everything goes ok, maybe is ffidl only able to open system dll's ?

    regards

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Ashok@21:1/5 to All on Sat Apr 16 11:01:17 2022
    On 4/16/2022 5:50 AM, pd wrote:
    I was trying to use ffidl to access functions defined in a dll located in the same folder of my tcl script.

    I'm using a windows machine executing the script both using cmd.exe and cygwin to execute "tclsh.exe myscript.tcl"

    Every attempt get the same error:

    couldn't load file "AutoItDLL.dll" : ???

    Two possibilities come to mind - it's a 32-bit/64-bit mismatch in
    either direction, or some support DLL that autoitdll.dll depends on that
    is missing (including possibly a C runtime version that is not
    installed on the system)

    /Ashok

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From pd@21:1/5 to All on Sat Apr 16 07:36:32 2022
    El sábado, 16 de abril de 2022 a las 7:31:21 UTC+2, Ashok escribió:
    On 4/16/2022 5:50 AM, pd wrote:
    I was trying to use ffidl to access functions defined in a dll located in the same folder of my tcl script.
    Every attempt get the same error:

    couldn't load file "AutoItDLL.dll" : ???

    Two possibilities come to mind - it's a 32-bit/64-bit mismatch in
    either direction, or some support DLL that autoitdll.dll depends on that
    is missing (including possibly a C runtime version that is not
    installed on the system)

    It seems it's a problem of arch mismatch, all local dlls I have tested are 32-bit compiled, I create a simple 64-bit dll just to test and it is loaded correctly and I can use the function.

    But I'm a bit confused because I've also copied the user32.dll from my system32 folder to my test folder and tried to load it from my local folder, getting "couldn¡t load file" error while using the system user32.dll works fine.

    My OS is a windows 10 x64 and I'm executing the tcl scripts both from cygwin (assume 32-bit) and windows cmd.exe, with same results.

    Here you are my tests and my conclusions, for every test I show the tcl script, the kind of dll and the script execution commad:

    [1] ------------------------ trying to load AutoItDLL.dll which is a 32bit i386 dll result: error loading dll
    $ cat ai.tcl
    lappend auto_path [pwd]\\Ffidl0.6
    package require Ffidl
    set dll [file nativename [pwd]\\AutoItDLL.dll]
    puts "$dll : [file exists $dll]"
    ffidl::callout AUTOIT_WinMinimizeAll {} int [ffidl::symbol $dll AUTOIT_WinMinimizeAll]
    AUTOIT_WinMinimizeAll

    $ file AutoItDLL.dll
    AutoItDLL.dll: PE32 executable (DLL) (GUI) Intel 80386, for MS Windows, UPX compressed

    $ tcl ai.tcl
    C:\tcl\AutoItDLL.dll : 1
    couldn't load file "C:\tcl\AutoItDLL.dll" : ???
    while executing
    "ffidl::symbol $dll AUTOIT_WinMinimizeAll"
    invoked from within
    "ffidl::callout AUTOIT_WinMinimizeAll {} int [ffidl::symbol $dll AUTOIT_WinMinimizeAll]"
    (file "ai.tcl" line 8)

    [2] ------------------------ trying to load system user32.dll result: success
    $ cat u.tcl
    lappend auto_path [pwd]\\Ffidl0.6
    package require Ffidl
    ffidl::callout findwin {pointer-utf8 pointer-utf8} long [ffidl::symbol user32 FindWindowA]
    puts "win: [findwin {} {}]"

    $ tcl u.tcl
    win: 0

    [3] ------------------------ trying to load user32.dll which is a copy of system32\user32.dll a 64 bit x86-64 dll result: error loading dll
    $ cat lu.tcl
    lappend auto_path [pwd]\\Ffidl0.6
    package require Ffidl
    set dll [file nativename [pwd]\\user32.dll]
    puts "$dll : [file exists $dll]"
    ffidl::callout findwin {pointer-utf8 pointer-utf8} long [ffidl::symbol $dll FindWindowA]
    puts "win: [findwin {} {}]"

    $ file user32.dll
    user32.dll: PE32+ executable (DLL) (GUI) x86-64, for MS Windows

    $ tcl lu.tcl
    C:\tcl\user32.dll : 1
    couldn't load file "C:\tcl\user32.dll" : ???
    while executing
    "ffidl::symbol $dll FindWindowA"
    invoked from within
    "ffidl::callout findwin {pointer-utf8 pointer-utf8} long [ffidl::symbol $dll FindWindowA]"
    (file "lu.tcl" line 9)

    [4] ------------------------ trying to load libhola.dll a test dll which only one function, it's a 64 bit x86-64 dll result: success
    $ cat f.tcl
    lappend auto_path [pwd]\\Ffidl0.6
    package require Ffidl
    set dll [file nativename [pwd]\\libhola.dll]
    puts "$dll : [file exists $dll]"
    ffidl::callout hola {pointer-utf8 } void [ffidl::symbol $dll hola ]
    hola {hola mundo!}

    $ file libhola.dll
    libhola.dll: PE32+ executable (DLL) (console) x86-64, for MS Windows

    $ tcl f.tcl
    C:\tcl\libhola.dll : 1
    hola mundo!


    What get me confused is user32.dll is the same kind of dll than libhola.dll : PE32+ executable (DLL) x86-64
    The only difference is libhola is a console DLL while user32.dll is a GUI DLL: libhola.dll: PE32+ executable (DLL) (console) x86-64, for MS Windows user32.dll: PE32+ executable (DLL) (GUI) x86-64, for MS Windows

    libhola.dll works ok when loaded from current dir but user32.dll doesn't work from current dir, it only works when using the system one (being both same arch, x86-64 64-bit)

    Any idea of what's happening here?

    regards

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From pd@21:1/5 to All on Sat Apr 16 07:48:03 2022
    El sábado, 16 de abril de 2022 a las 16:36:34 UTC+2, pd escribió:
    Two possibilities come to mind - it's a 32-bit/64-bit mismatch in
    either direction, or some support DLL that autoitdll.dll depends on that is missing (including possibly a C runtime version that is not
    installed on the system)
    It seems it's a problem of arch mismatch, all local dlls I have tested are 32-bit compiled, I create a simple 64-bit dll just to test and it is loaded correctly and I can use the function.

    another question, Is it possible to load 32-bit dll or 64-bit dll on demand from a tcl script using ffdi ? I mean, I can choose to load 32-bit version or 64-bit version (for example chossing the right ffidl.dll ) or I'm constrained by the machine arch?
    I ask this because the ffidl.dll I'm using is a 32-bit dll and it seems to load only 64-bit dll

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Ashok@21:1/5 to All on Sun Apr 17 21:00:10 2022
    On 4/16/2022 8:06 PM, pd wrote:
    bhola.dll works ok when loaded from current dir but user32.dll doesn't
    work from current dir, it only works when using the system one (being
    both same arch, x86-64 64-bit)

    Any idea of what's happening here?

    regards


    I do not remember the details, but I think Windows has special handling
    for the system DLLs (like user32.dll). It enforces that they have to be
    loaded from the system directory (to prevent some type of malware).

    I could be wrong.


    /Ashok

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Ashok@21:1/5 to All on Sun Apr 17 20:58:07 2022
    On 4/16/2022 8:18 PM, pd wrote:
    El sábado, 16 de abril de 2022 a las 16:36:34 UTC+2, pd escribió:
    Two possibilities come to mind - it's a 32-bit/64-bit mismatch in
    either direction, or some support DLL that autoitdll.dll depends on that >>> is missing (including possibly a C runtime version that is not
    installed on the system)
    It seems it's a problem of arch mismatch, all local dlls I have tested are 32-bit compiled, I create a simple 64-bit dll just to test and it is loaded correctly and I can use the function.

    another question, Is it possible to load 32-bit dll or 64-bit dll on demand from a tcl script using ffdi ? I mean, I can choose to load 32-bit version or 64-bit version (for example chossing the right ffidl.dll ) or I'm constrained by the machine
    arch? I ask this because the ffidl.dll I'm using is a 32-bit dll and it seems to load only 64-bit dll

    From a 32-bit Tcl, ffidl.dll must also be 32-bit and the DLL you are
    trying to load must also be the same. No way around it.

    Ditto for 64-bit.

    I cannot see how you might be using a 64-bit dll from a 32-bit ffidl.
    It's simply not possible.

    /Ashok

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)
  • From Stephan Effelsberg@21:1/5 to All on Mon May 9 12:40:40 2022
    I'm juggling with 32-bit and 64-bit DLLs myself from time to time. When working with system DLLs, you'll get the version that fits the bitness of the requesting process. Be aware of the File System Redirector:

    https://docs.microsoft.com/en-us/windows/win32/winprog64/file-system-redirector

    Try it yourself: Use the Windows command line to make a copy of user32.dll
    copy c:\Windows\System32\user32.dll <somewhere>
    You'll get a 64-bit copy of the DLL, you can even inspect the file with a simple text editor to verify this. Search for the string "PE", it's near the start of the file (offset 232, methinks). The third character after PE is "d" for a 64-bit PE and "L"
    for a 32-bit PE.

    Now use a 32-bit shell, e.g. a 32-bit Tclkit.
    file copy c:/Windows/System32/user32.dll <somewhereelse>
    You'll get the 32-bit copy of that DLL.

    -- Stephan

    --- SoupGate-Win32 v1.05
    * Origin: fsxNet Usenet Gateway (21:1/5)