lua-users home
lua-l archive

[Date Prev][Date Next][Thread Prev][Thread Next] [Date Index] [Thread Index]


I'm battling with similar problem, in my case all executables (luajit) and dynamic libraries are in one directory. On Windows this works fine (but would not have I put lua.exe in different folder, then I would have to add PATH=<dll-path>;%PATH%)

So far only Mac OS X can provide solution that you need through @rpath, and @executable_path path names that can be put in the library, such way that dll's and executables are in different folders. Combined with universal support this makes it easiest platform to handle.

Linux also has rpath, but it has to be absolute :(, hence LD_LIBRARY_PATH (or other tricks)

On 8/27/11 8:48 AM, Should Pain wrote:
于 2011-8-27 23:23, Lorenzo Donati 写道:
On 27/08/2011 16.58, Should Pain wrote:
于 2011-8-26 21:44, Lorenzo Donati 写道:
Hi All!

Some time ago I wanted to clean up my C search path, which began
looking as a trash bin full of unrelated DLLs side by side to lua.exe.

I tried to put different libraries in different subdirs, but then for
example this idiom didn't work any longer:

local lfs = require 'lfs'

if I did not mis-understood you, maybe what you could try is like this
(see the document for `package.cpath'):

>
> -- suppose you have already set the variable `root'
> -- ROOT = "/"
> package.cpath = ROOT .. "/?/?.dll" .. package.cpath
>

>
> -- or for windows, maybe use this form
> package.cpath = ROOT .. "\\?\\?.dll" .. package.cpath
>

then, this statement
>
> require "lpeg"
>
would just load "ROOT/lpeg/lpeg.so" or "ROOT\lpeg\lpeg.dll"

Thank you for the feedback.

Yes I know that, but this works just because lpeg has only one DLL
which depends only on known system DLLs. It won't work with other
libraries consisting of more than one DLLs that link to each other.

This is definitely a Windows issue - by default the Windows dynamic
linker resolves the links starting from the directory where the
executable is placed - in this case lua.exe. But if in a Lua script I
have:

require 'foo'


and the library 'foo' is implemented as foo.dll, and this in turn is
linked against bar.dll, then when loading foo.dll, the dynamic linker
will look for bar.dll in the directory of lua.exe, not in the
directory of foo.dll. So the "dirty" solution is to place every dll
side by side to lua.exe, which is a mess (the term "DLL hell" was
coined to describe this).

One could use the Windows API function LoadLibraryEx with a special
flag: LOAD_WITH_ALTERED_SEARCH_PATH, which changes the default
behaviour of the dynamic linker, but this requires changing Lua
sources (I did that already and it goes ok). The problem is that I use
several different Lua versions (5.1.4, customized 5.1.4, 5.2) and I
want to keep my library in one place without duplicating them. So my
complicated solution was an attempt to keep all my "interpreters" happy.

The big IF is that I don't know if what I did is ok, within the limits
of the approach, or if it is a time bomb waiting to explode in my face
:-)

-- Lorenzo



well, in fact the search path when Windows loads a dll is as following
(in order)(see MSDN):

 1.

    The directory where the executable module for the current process is
    located.

 2.

    The current directory.

 3.

    The Windows system directory. The *GetSystemDirectory* function
    retrieves the path of this directory.

 4.

    The Windows directory. The *GetWindowsDirectory *function retrieves
    the path of this directory.

 5.

    The directories listed in the PATH environment variable.



when the dependenies are not so many, I would prefer to put them into
one single directory, and add this directory to the PATH envirenment
variable(on Linux, the LD_LIBRARY_PATH variable)

I can set the env in user login/startup script, or in lua script.

I don't like to scatter dlls in many directories. at all, they are
SHARED libraries, and there should not be so many of them.


But I suppose this is more about personal taste.

since you would only run it on Windows, you could just do it in platform
(Windows) specific way as package.loadlib or so.

as long as you don't move to different platform, the package.loadlib
works just fine. nothing to worry.


My opinion. Hopefully useful.