CDE
This commit is contained in:
parent
518da4a923
commit
764da6cbbb
6144 changed files with 83610 additions and 11 deletions
6
Task/Call-a-function-in-a-shared-library/0DESCRIPTION
Normal file
6
Task/Call-a-function-in-a-shared-library/0DESCRIPTION
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
Show how to call a function in a shared library (without dynamically linking to it at compile-time). In particular, show how to call the shared library function if the library is available, otherwise use an internal equivalent function.
|
||||
|
||||
This is a special case of [[Call foreign language function|calling a foreign language function]] where the focus is close to the ABI level and not at the normal API level.
|
||||
|
||||
===Related tasks===
|
||||
* [[OpenGL]] -- OpenGL is usually maintained as a shared library.
|
||||
2
Task/Call-a-function-in-a-shared-library/1META.yaml
Normal file
2
Task/Call-a-function-in-a-shared-library/1META.yaml
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
---
|
||||
note: Programming environment operations
|
||||
|
|
@ -0,0 +1,45 @@
|
|||
with Ada.Text_IO; use Ada.Text_IO;
|
||||
with Interfaces; use Interfaces;
|
||||
with Interfaces.C; use Interfaces.C;
|
||||
with System; use System;
|
||||
|
||||
with Ada.Unchecked_Conversion;
|
||||
|
||||
procedure Shared_Library_Call is
|
||||
--
|
||||
-- Interface to kernel32.dll which is resposible for loading DLLs under Windows.
|
||||
-- There are ready to use Win32 binding. We don't want to use them here.
|
||||
--
|
||||
type HANDLE is new Unsigned_32;
|
||||
function LoadLibrary (lpFileName : char_array) return HANDLE;
|
||||
pragma Import (stdcall, LoadLibrary, "LoadLibrary", "_LoadLibraryA@4");
|
||||
|
||||
function GetProcAddress (hModule : HANDLE; lpProcName : char_array)
|
||||
return Address;
|
||||
pragma Import (stdcall, GetProcAddress, "GetProcAddress", "_GetProcAddress@8");
|
||||
--
|
||||
-- The interface of the function we want to call. It is a pointer (access type)
|
||||
-- because we will link it dynamically. The function is from User32.dll
|
||||
--
|
||||
type MessageBox is access function
|
||||
( hWnd : Address := Null_Address;
|
||||
lpText : char_array;
|
||||
lpCaption : char_array := To_C ("Greeting");
|
||||
uType : Unsigned_16 := 0
|
||||
) return Integer_16;
|
||||
pragma Convention (Stdcall, MessageBox);
|
||||
function To_MessageBox is new Ada.Unchecked_Conversion (Address, MessageBox);
|
||||
|
||||
Library : HANDLE := LoadLibrary (To_C ("user32.dll"));
|
||||
Pointer : Address := GetProcAddress (Library, To_C ("MessageBoxA"));
|
||||
begin
|
||||
if Pointer /= Null_Address then
|
||||
declare
|
||||
Result : Integer_16;
|
||||
begin
|
||||
Result := To_MessageBox (Pointer) (lpText => To_C ("Hello!"));
|
||||
end;
|
||||
else
|
||||
Put_Line ("Unable to load the library " & HANDLE'Image (Library));
|
||||
end if;
|
||||
end Shared_Library_Call;
|
||||
|
|
@ -0,0 +1,49 @@
|
|||
with Ada.Environment_Variables; use Ada.Environment_Variables;
|
||||
with Ada.Text_IO; use Ada.Text_IO;
|
||||
with Interfaces; use Interfaces;
|
||||
with Interfaces.C; use Interfaces.C;
|
||||
with System; use System;
|
||||
|
||||
with Ada.Unchecked_Conversion;
|
||||
|
||||
procedure Shared_Library_Call is
|
||||
--
|
||||
-- Interface to libdl to load dynamically linked libraries
|
||||
--
|
||||
function dlopen (FileName : char_array; Flag : int) return Address;
|
||||
pragma Import (C, dlopen);
|
||||
|
||||
function dlsym (Handle : address; Symbol : char_array) return Address;
|
||||
pragma Import (C, dlsym);
|
||||
--
|
||||
-- The interfaces of the functions we want to call. These are pointers
|
||||
-- (access type) because we will link it dynamically. The functions
|
||||
-- come from libX11.so.
|
||||
--
|
||||
type XOpenDisplay is access function (Display_Name : char_array) return Address;
|
||||
pragma Convention (C, XOpenDisplay);
|
||||
function To_Ptr is new Ada.Unchecked_Conversion (Address, XOpenDisplay);
|
||||
|
||||
type XDisplayWidth is access function (Display : Address; Screen : int) return int;
|
||||
pragma Convention (C, XDisplayWidth);
|
||||
function To_Ptr is new Ada.Unchecked_Conversion (Address, XDisplayWidth);
|
||||
|
||||
Library : Address := dlopen (To_C ("libX11.so"), 1);
|
||||
OpenDisplay : XOpenDisplay := To_Ptr (dlsym (Library, To_C ("XOpenDisplay")));
|
||||
DisplayWidth : XDisplayWidth := To_Ptr (dlsym (Library, To_C ("XDisplayWidth")));
|
||||
begin
|
||||
if OpenDisplay /= null and then DisplayWidth /= null then
|
||||
declare
|
||||
Display : Address;
|
||||
begin
|
||||
Display := OpenDisplay (To_C (Value ("DISPLAY")));
|
||||
if Display = Null_Address then
|
||||
Put_Line ("Unable to open display " & Value ("DISPLAY"));
|
||||
else
|
||||
Put_Line (Value ("DISPLAY") & " width is" & int'image (DisplayWidth (Display, 0)));
|
||||
end if;
|
||||
end;
|
||||
else
|
||||
Put_Line ("Unable to load the library");
|
||||
end if;
|
||||
end Shared_Library_Call;
|
||||
|
|
@ -0,0 +1,3 @@
|
|||
ahkdll := DllCall("LoadLibrary", "str", "AutoHotkey.dll")
|
||||
clientHandle := DllCall("AutoHotkey\ahkdll", "str", "dllclient.ahk", "str"
|
||||
, "", "str", "parameter1 parameter2", "Cdecl Int")
|
||||
|
|
@ -0,0 +1 @@
|
|||
Msgbox, hello from client
|
||||
|
|
@ -0,0 +1 @@
|
|||
SYS "MessageBox", @hwnd%, "This is a test message", 0, 0
|
||||
|
|
@ -0,0 +1,36 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <dlfcn.h>
|
||||
|
||||
int myopenimage(const char *in)
|
||||
{
|
||||
static int handle=0;
|
||||
fprintf(stderr, "internal openimage opens %s...\n", in);
|
||||
return handle++;
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
void *imglib;
|
||||
int (*extopenimage)(const char *);
|
||||
int imghandle;
|
||||
|
||||
imglib = dlopen("./fakeimglib.so", RTLD_LAZY);
|
||||
if ( imglib != NULL ) {
|
||||
/* extopenimage = (int (*)(const char *))dlsym(imglib,...)
|
||||
"man dlopen" says that C99 standard leaves casting from
|
||||
"void *" to a function pointer undefined. The following is the
|
||||
POSIX.1-2003 workaround found in man */
|
||||
*(void **)(&extopenimage) = dlsym(imglib, "openimage");
|
||||
/* the following works with gcc, gives no warning even with
|
||||
-Wall -std=c99 -pedantic options... :D */
|
||||
/* extopenimage = dlsym(imglib, "openimage"); */
|
||||
imghandle = extopenimage("fake.img");
|
||||
} else {
|
||||
imghandle = myopenimage("fake.img");
|
||||
}
|
||||
printf("opened with handle %d\n", imghandle);
|
||||
/* ... */
|
||||
if (imglib != NULL ) dlclose(imglib);
|
||||
return EXIT_SUCCESS;
|
||||
}
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
#include <stdio.h>
|
||||
/* gcc -shared -nostartfiles fakeimglib.c -o fakeimglib.so */
|
||||
int openimage(const char *s)
|
||||
{
|
||||
static int handle = 100;
|
||||
fprintf(stderr, "opening %s\n", s);
|
||||
return handle++;
|
||||
}
|
||||
|
|
@ -0,0 +1,7 @@
|
|||
CL-USER> (cffi:load-foreign-library "libX11.so")
|
||||
#<CFFI::FOREIGN-LIBRARY {1004F4ECC1}>
|
||||
CL-USER> (cffi:foreign-funcall "XOpenDisplay"
|
||||
:string #+sbcl (sb-posix:getenv "DISPLAY")
|
||||
#-sbcl ":0.0"
|
||||
:pointer)
|
||||
#.(SB-SYS:INT-SAP #X00650FD0)
|
||||
|
|
@ -0,0 +1,9 @@
|
|||
pragma(lib, "user32.lib");
|
||||
|
||||
import std.stdio, std.c.windows.windows;
|
||||
|
||||
extern(Windows) UINT GetDoubleClickTime();
|
||||
|
||||
void main() {
|
||||
writeln(GetDoubleClickTime());
|
||||
}
|
||||
|
|
@ -0,0 +1 @@
|
|||
procedure DoSomething; external 'MYLIB.DLL';
|
||||
|
|
@ -0,0 +1 @@
|
|||
procedure DoSomething; external 'MYLIB.DLL' delayed;
|
||||
|
|
@ -0,0 +1,12 @@
|
|||
var
|
||||
lLibraryHandle: THandle;
|
||||
lDoSomething: procedure; stdcall;
|
||||
begin
|
||||
lLibraryHandle := LoadLibrary('MYLIB.DLL');
|
||||
if lLibraryHandle >= 32 then { success }
|
||||
begin
|
||||
lDoSomething := GetProcAddress(lLibraryHandle, 'DoSomething');
|
||||
lDoSomething();
|
||||
FreeLibrary(lLibraryHandle);
|
||||
end;
|
||||
end;
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
public class LoadLib{
|
||||
private static native void functionInSharedLib(); //change return type or parameters as necessary
|
||||
|
||||
public static void main(String[] args){
|
||||
System.loadLibrary("Path/to/library/here/lib.dll");
|
||||
functionInSharedLib();
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,15 @@
|
|||
import com.sun.jna.Library;
|
||||
import com.sun.jna.Native;
|
||||
|
||||
public class LoadLibJNA{
|
||||
private interface YourSharedLibraryName extends Library{
|
||||
//put shared library functions here with no definition
|
||||
public void sharedLibraryfunction();
|
||||
}
|
||||
|
||||
public static void main(String[] args){
|
||||
YourSharedLibraryName lib = (YourSharedLibraryName)Native.loadLibrary("sharedLibrary",//as in "sharedLibrary.dll"
|
||||
YourSharedLibraryName.class);
|
||||
lib.sharedLibraryFunction();
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,26 @@
|
|||
(load "@lib/gcc.l")
|
||||
|
||||
(gcc "x11" '("-lX11") 'xOpenDisplay 'xCloseDisplay)
|
||||
|
||||
#include <X11/Xlib.h>
|
||||
|
||||
any xOpenDisplay(any ex) {
|
||||
any x = evSym(cdr(ex)); // Get display name
|
||||
char display[bufSize(x)]; // Create a buffer for the name
|
||||
|
||||
bufString(x, display); // Upack the name
|
||||
return boxCnt((long)XOpenDisplay(display));
|
||||
}
|
||||
|
||||
any xCloseDisplay(any ex) {
|
||||
return boxCnt(XCloseDisplay((Display*)evCnt(ex, cdr(ex))));
|
||||
}
|
||||
/**/
|
||||
|
||||
# With that we can open and close the display:
|
||||
: (setq Display (xOpenDisplay ":0.7")) # Wrong
|
||||
-> 0
|
||||
: (setq Display (xOpenDisplay ":0.0")) # Correct
|
||||
-> 158094320
|
||||
: (xCloseDisplay Display)
|
||||
-> 0
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
: (setq Display (native "/usr/lib/libX11.so.6" "XOpenDisplay" 'N ":0.0"))
|
||||
-> 6502688
|
||||
: (native "/usr/lib/libX11.so.6" "XCloseDisplay" 'I Display)
|
||||
-> 0
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
import ctypes
|
||||
|
||||
user32_dll = ctypes.cdll.LoadLibrary('User32.dll')
|
||||
print user32_dll.GetDoubleClickTime()
|
||||
|
|
@ -0,0 +1,6 @@
|
|||
#lang racket
|
||||
(require ffi/unsafe)
|
||||
(define libm (ffi-lib "libm")) ; get a handle for the C math library
|
||||
; look up sqrt in the math library. if we can't find it, return the builtin sqrt
|
||||
(define extern-sqrt (get-ffi-obj 'sqrt libm (_fun _double -> _double)
|
||||
(lambda () sqrt)))
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
require 'dl/import'
|
||||
|
||||
FakeImgLib = DL.dlopen("/path/to/fakeimg.so")
|
||||
|
||||
module FakeImage
|
||||
def self.openimage filename
|
||||
FakeImgLib["openimage", "IS"].call(filename)[0]
|
||||
end
|
||||
end
|
||||
|
||||
handle = FakeImage.openimage("path/to/image")
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
require 'ffi'
|
||||
module FakeImgLib
|
||||
extend FFI::Library
|
||||
ffi_lib "path/to/fakeimglib.so"
|
||||
attach_function :openimage, [:string], :int
|
||||
end
|
||||
|
||||
handle = FakeImgLib.openimage("path/to/image")
|
||||
|
|
@ -0,0 +1,14 @@
|
|||
DLD addLibrary: 'fakeimglib'.
|
||||
|
||||
Object subclass: ExtLib [
|
||||
ExtLib class >> openimage: aString [
|
||||
(CFunctionDescriptor isFunction: 'openimage')
|
||||
ifTrue: [
|
||||
(CFunctionDescriptor for: 'openimage'
|
||||
returning: #int
|
||||
withArgs: #( #string ) ) callInto: (ValueHolder null).
|
||||
] ifFalse: [ ('internal open image %1' % { aString }) displayNl ]
|
||||
]
|
||||
].
|
||||
|
||||
ExtLib openimage: 'test.png'.
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
package require Ffidl
|
||||
|
||||
if {[catch {
|
||||
ffidl::callout OpenImage {pointer-utf8} int [ffidl::symbol fakeimglib.so openimage]
|
||||
}]} then {
|
||||
# Create the OpenImage command by other means here...
|
||||
}
|
||||
set handle [OpenImage "/the/file/name"]
|
||||
Loading…
Add table
Add a link
Reference in a new issue