Lua Proxy Dll Two |
|
The utility can build proxy DLL's for hosts of any kind, it is not restricted by Lua-related hosts.
The utility assumes (and requires) MinGW development system.
The utility contains one "public" function: CreateProxyDll
. The function accepts one argument, a table, that must have the following fields specified:
PROXY : (path)name of the proxy DLL to build HOST : (path)name of the host library file (file must exist) DEFFILE : (path)name of the definition file (file must exist)
Example 1: allow combined use of applications or libraries linked with either of lua5.1.dll and lua51.dll:
CreateProxyDll { PROXY = "lua51.dll", HOST = "c:\\exe\\lua5.1.dll", DEFFILE = "liblua5.1.def", }
Example 2: make possible for a statically built Lua interpreter to safely require()
external libraries:
CreateProxyDll { PROXY = "lua5.1.dll", HOST = "c:\\exe\\lua51x.exe", DEFFILE = "liblua5.1.def", }
mkproxy.lua:
-- Name: mkproxy.lua -- Goal: Create a proxy DLL that redirects all calls to the "host" library -- Written by: Shmuel Zeigerman -- License: public domain local CFile = [[ #include <windows.h> BOOL WINAPI DllMain (HINSTANCE hinstDLL, DWORD Reason, LPVOID Reserved) { return TRUE; } ]] local function execute(s) assert(0 == os.execute(s)) end local function CreateObjectFile (objname) assert(objname:match("%.o$")) local cname = objname:gsub("%.o$", ".c") local fp = assert(io.open(cname, "w")) fp:write (CFile) fp:close() execute("gcc -c " .. cname .. " -o " .. objname) os.remove(cname) end function CreateProxyDll (config) assert(type(config) == "table", "argument #1: a table expected") assert(config.PROXY, "config.PROXY not specified") assert(config.HOST, "config.HOST not specified") assert(config.DEFFILE, "config.DEFFILE not specified") assert(io.open(config.HOST)):close() assert(io.open(config.DEFFILE)):close() ----------------------------------------------------------------------------- local hostpath, hostname = config.HOST:match ("^(.+)[\\/](.+)$") if not hostpath then hostpath, hostname = ".", config.HOST end local temp_dll = (hostname:sub(-4):lower() ~= ".dll") and "temp_dll.dll" local temp_obj = "temp_obj.o" CreateObjectFile(temp_obj) local cmdline = table.concat ({ "gcc -shared -s -nostdlib", temp_obj, config.DEFFILE, "-L" .. (temp_dll and "." or hostpath), "-l" .. (temp_dll or hostname):sub(1,-5), "-o" .. config.PROXY, }, " ") if temp_dll then execute("copy " .. config.HOST .. " " .. temp_dll) end execute(cmdline) os.remove(temp_obj) if temp_dll then os.remove(temp_dll) end end
The following build is for MSVC2005. It uses the "nodefaultlib" linker option. The final proxy DLL was about 9 KB.
local DEFFILE = "lua5.1.def" -- .def file for lua5.1.dll local LIBFILE = "lua5.1.lib" -- .lib file for lua5.1.dll local CFILE = "luaproxy.c"-- output file local MAKFILE = "luaproxy.mak" -- output file ---------------------------------------------------------------------- local cfile = assert(io.open(CFILE, "w")) cfile:write [=[ #include <windows.h> BOOL APIENTRY DllMain(HANDLE module, DWORD reason, LPVOID reserved) { return TRUE; } ]=] cfile:close() ---------------------------------------------------------------------- local makfile = assert(io.open(MAKFILE, "w")) makfile:write(string.format([=[ lua51.dll : luaproxy.c cl -I../lua/src /O2 /LD /GS- luaproxy.c /link /def:%s %s \ /out:lua51.dll /nodefaultlib /entry:DllMain ]=], DEFFILE, LIBFILE)) makfile:close() ----------------------------------------------------------------------
It seems that what you are doing is building an empty C file which links to the stubs in the import library, and reexposing those stubs as a dll interface. This would mean that the DLL you generate:
Tell me if I misunderstood your code.