Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update master #1

Merged
merged 37 commits into from
Aug 19, 2016
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
37 commits
Select commit Hold shift + click to select a range
2192d19
Fix bug with operator precendence
omus Aug 16, 2016
d2bbdd2
Improve URL regex
omus Aug 16, 2016
749d099
Correct invalid SSH URL
omus Aug 16, 2016
575f2ae
move recheck_tuple_intersection to thread-local
vtjnash Aug 17, 2016
b6b26df
ensure in_typeinf_loop is only read by the thread with the typeinf lock
vtjnash Aug 17, 2016
1e98a5a
Removed SSH test from libgit2-online
omus Aug 17, 2016
ea8fa25
Update URL parsing tests
omus Aug 17, 2016
1df4454
Add tests for flipdim, unary ops
kshyatt Aug 17, 2016
07ee045
Add tests for iteration methods on numbers
kshyatt Aug 17, 2016
22df25e
split static-eval to its individual users
vtjnash Aug 17, 2016
0f805fb
updates to README.md (#18093)
mcprentiss Aug 18, 2016
50f30f4
Merge pull request #18094 from JuliaLang/jn/thread-fixes
vtjnash Aug 18, 2016
6a62d30
improve FreeBSD / generic posix support
vtjnash Aug 16, 2016
2041bbe
Merge pull request #18092 from JuliaLang/ksh/unaryandnum
kshyatt Aug 18, 2016
68ba177
Added test for complex on SharedArrays (#18097)
kshyatt Aug 18, 2016
1af5356
Set LIB_INSTALL_DIR for cmake-based projects (#18047)
staticfloat Aug 18, 2016
d3951aa
readme formatting
tkelman Aug 18, 2016
e711097
Fix compiler warnings on 32bits
yuyichao Aug 18, 2016
760bc41
Improve arch/cpu detection/selection on ARM and AArch64
yuyichao Aug 18, 2016
5977167
fix "recommanded" typo
tkelman Aug 18, 2016
2d9f3a7
ASAN: provide default options.
maleadt Aug 16, 2016
030ff40
ASAN/MSAN: document use of sanitizers.
maleadt Aug 16, 2016
3cbc05d
Merge pull request #18067 from JuliaLang/tb/asan_doc
maleadt Aug 18, 2016
3feef68
Missing tests for strings (#18089)
kshyatt Aug 18, 2016
6625c03
factor out the jl_get_llvmf code more cleanly
vtjnash Aug 17, 2016
54f5b59
Merge pull request #18099 from JuliaLang/jn/static-eval-less
vtjnash Aug 18, 2016
650a885
Merge pull request #18108 from JuliaLang/yyc/warnings
vtjnash Aug 18, 2016
adecd73
Merge pull request #18063 from JuliaLang/jn/freebsd
vtjnash Aug 18, 2016
090e9e4
Fix compilation on llvm 3.9
yuyichao Aug 18, 2016
4e12052
Build curl with minimal external libraries.
ViralBShah Aug 18, 2016
b506041
make dlopen more conservative about opening files the user didn't req…
stevengj Aug 18, 2016
a67a95e
Merge pull request #18066 from omus/libgit2-fixes
StefanKarpinski Aug 18, 2016
c74b7d0
Merge pull request #18087 from JuliaLang/jn/linfo-reflect
vtjnash Aug 18, 2016
02246d8
Merge pull request #18104 from JuliaLang/yyc/tests/llvm
vtjnash Aug 18, 2016
03a9654
Merge pull request #18103 from JuliaLang/vs/curl
vtjnash Aug 18, 2016
04047f6
Merge pull request #18100 from JuliaLang/yyc/threads/arm
vtjnash Aug 18, 2016
57df5f1
Add istriu, istril, issymmetric, and ishermitian methods for UniformS…
andreasnoack Aug 18, 2016
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions Make.inc
Original file line number Diff line number Diff line change
Expand Up @@ -340,6 +340,11 @@ endif

STDLIBCPP_FLAG :=

ifeq ($(OS), FreeBSD)
USEGCC := 0
USECLANG := 1
endif

ifeq ($(OS), Darwin)
DARWINVER := $(shell uname -r | cut -b 1-2)
DARWINVER_GTE13 := $(shell expr `uname -r | cut -b 1-2` \>= 13)
Expand Down
7 changes: 6 additions & 1 deletion README.arm.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,12 @@
# Julia binaries for ARM

[Nightly builds](https://status.julialang.org/download/linux-arm) are
available for ARM.
available for ARMv7-A.

# Hardware requirements

Julia requires at least `armv6` and `vfpv2` instruction sets. It's recommended
to use at least `armv7-a`. `armv5` or soft float are not supported.

# Building Julia on ARM

Expand Down
16 changes: 13 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ developers may find the notes in [CONTRIBUTING](https://github.com/JuliaLang/jul
- **FreeBSD**
- **Windows**

All systems are supported with both x86/64 (64-bit) and x86 (32-bit) architectures. Experimental and early support for [ARM](https://github.com/JuliaLang/julia/blob/master/README.arm.md) is available too.
All systems are supported with both x86/64 (64-bit) and x86 (32-bit) architectures. Experimental and early support for [ARM](https://github.com/JuliaLang/julia/blob/master/README.arm.md), AARCH64, and POWER (little-endian) is available too.

<a name="Source-Download-and-Compilation"/>
## Source Download and Compilation
Expand Down Expand Up @@ -235,12 +235,22 @@ When building Julia, or its dependencies, libraries installed by third party pac

### FreeBSD

On *FreeBSD Release 9.0*, install the `gcc47`, `git`, and `gmake` packages/ports, and compile Julia with the command:
On *FreeBSD Release 11.0*, install the gfortran, git, cmake, and gmake packages/ports (`pkg install gcc6 gmake git cmake`), and compile Julia with the command:

$ gmake FC=gfortran47
$ echo 'FC=gfortran6' >> Make.user
$ gmake

You must use the `gmake` command on FreeBSD instead of `make`.

Note that Julia is community-supported and we have little control over our upstream dependencies, you may still run into issues with dependencies and YMMV. Current known issues include:

- The x86 arch doesn't support threading due to lack of compiler runtime library support (set `JULIA_THREADS=0`).
- libunwind needs a small patch to its tests to compile.
- OpenBLAS patches in pkg haven't been upstreamed.
- gfortran can't link binaries. Set `FFLAGS=-Wl,-rpath,/usr/local/lib/gcc6` to work around this (upstream bug submitted to FreeBSD pkg maintainers).
- System libraries installed by pkg are not on the compiler path by default. You may need to add `LDFLAGS=/usr/local/lib` and `CPPFLAGS=/usr/local/include` to your environment or `Make.user` file to build successfully.


### Windows

In order to build Julia on Windows, see [README.windows](https://github.com/JuliaLang/julia/blob/master/README.windows.md).
Expand Down
6 changes: 5 additions & 1 deletion base/inference.jl
Original file line number Diff line number Diff line change
Expand Up @@ -1469,7 +1469,11 @@ function typeinf_edge(method::Method, atypes::ANY, sparams::SimpleVector, needtr
end
end

if caller === nothing && in_typeinf_loop
ccall(:jl_typeinf_begin, Void, ())
thread_in_typeinf_loop = in_typeinf_loop::Bool
ccall(:jl_typeinf_end, Void, ())

if caller === nothing && thread_in_typeinf_loop
# if the caller needed the ast, but we are already in the typeinf loop
# then just return early -- we can't fulfill this request
# if the client was inlining, then this means we decided not to try to infer this
Expand Down
6 changes: 6 additions & 0 deletions base/libdl.jl
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,12 @@ end

Load a shared library, returning an opaque handle.

The extension given by the constant `dlext` (`.so`, `.dll`, or `.dylib`)
can be omitted from the `libfile` string, as it is automatically appended
if needed. If `libfile` is not an absolute path name, then the paths
in the array `DL_LOAD_PATH` are searched for `libfile`, followed by the
system load path.

The optional flags argument is a bitwise-or of zero or more of `RTLD_LOCAL`, `RTLD_GLOBAL`,
`RTLD_LAZY`, `RTLD_NOW`, `RTLD_NODELETE`, `RTLD_NOLOAD`, `RTLD_DEEPBIND`, and `RTLD_FIRST`.
These are converted to the corresponding flags of the POSIX (and/or GNU libc and/or MacOS)
Expand Down
12 changes: 5 additions & 7 deletions base/libgit2/callbacks.jl
Original file line number Diff line number Diff line change
Expand Up @@ -160,7 +160,7 @@ function authenticate_userpass(creds::UserPasswordCredentials, libgit2credptr::P
urlusername : username)
userpass = prompt("Password for '$schema$username@$host'", password=true)
end
(creds.user != username) || (creds.pass != userpass) && reset!(creds)
((creds.user != username) || (creds.pass != userpass)) && reset!(creds)
creds.user = username # save credentials
creds.pass = userpass # save credentials

Expand Down Expand Up @@ -209,12 +209,10 @@ function credentials_callback(libgit2credptr::Ptr{Ptr{Void}}, url_ptr::Cstring,
url = unsafe_string(url_ptr)

# parse url for schema and host
urlparts = match(urlmatcher, url)
schema = urlparts.captures[1]
urlusername = urlparts.captures[4]
urlusername = urlusername === nothing ? "" : String(urlusername)
host = urlparts.captures[5]
schema = schema === nothing ? "" : schema*"://"
urlparts = match(URL_REGEX, url)
schema = urlparts[:scheme] === nothing ? "" : urlparts[:scheme] * "://"
urlusername = urlparts[:user] === nothing ? "" : urlparts[:user]
host = urlparts[:host]

# get credentials object from payload pointer
@assert payload_ptr != C_NULL
Expand Down
8 changes: 7 additions & 1 deletion base/libgit2/utils.jl
Original file line number Diff line number Diff line change
@@ -1,6 +1,12 @@
# This file is a part of Julia. License is MIT: http://julialang.org/license

const urlmatcher = r"^(http[s]?|git|ssh)?(:\/\/)?((\w+)@)?([A-Za-z0-9\-\.]+)(:[0-9]+)?(.*)$"
const URL_REGEX = r"""
^(?:(?<scheme>https?|git|ssh)\:\/\/)?
(?:(?<user>.*?)(?:\:(?<password>.*?))?@)?
(?<host>[A-Za-z0-9\-\.]+)
(?:\:(?<port>\d+)?)?
(?<path>.*?)$
"""x

function version()
major = Ref{Cint}(0)
Expand Down
5 changes: 5 additions & 0 deletions base/linalg/uniformscaling.jl
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,11 @@ one{T}(J::UniformScaling{T}) = one(UniformScaling{T})
zero{T}(::Type{UniformScaling{T}}) = UniformScaling(zero(T))
zero{T}(J::UniformScaling{T}) = zero(UniformScaling{T})

istriu(::UniformScaling) = true
istril(::UniformScaling) = true
issymmetric(::UniformScaling) = true
ishermitian(J::UniformScaling) = isreal(J.λ)

(+)(J1::UniformScaling, J2::UniformScaling) = UniformScaling(J1.λ+J2.λ)
(+){T}(B::BitArray{2},J::UniformScaling{T}) = Array(B) + J
(+)(J::UniformScaling, B::BitArray{2}) = J + Array(B)
Expand Down
41 changes: 32 additions & 9 deletions base/reflection.jl
Original file line number Diff line number Diff line change
Expand Up @@ -339,26 +339,44 @@ uncompressed_ast(l::LambdaInfo) =
isa(l.code,Array{UInt8,1}) ? ccall(:jl_uncompress_ast, Array{Any,1}, (Any,Any), l, l.code) : l.code

# Printing code representations in IR and assembly
function _dump_function(f, t::ANY, native, wrapper, strip_ir_metadata, dump_module)
ccall(:jl_is_in_pure_context, Bool, ()) && error("native reflection cannot be used from generated functions")
function _dump_function(f::ANY, t::ANY, native::Bool, wrapper::Bool, strip_ir_metadata::Bool, dump_module::Bool)
ccall(:jl_is_in_pure_context, Bool, ()) && error("code reflection cannot be used from generated functions")
if isa(f, Core.Builtin)
throw(ArgumentError("argument is not a generic function"))
end
t = tt_cons(Core.Typeof(f), to_tuple_type(t))
llvmf = ccall(:jl_get_llvmf, Ptr{Void}, (Any, Bool, Bool), t, wrapper, native)
# get the LambdaInfo for the method match
meth = which(f, t)
t = to_tuple_type(t)
ft = isa(f, Type) ? Type{f} : typeof(f)
tt = Tuple{ft, t.parameters...}
(ti, env) = ccall(:jl_match_method, Any, (Any, Any, Any),
tt, meth.sig, meth.tvars)::SimpleVector
li = func_for_method_checked(meth, tt)
# try to infer it
(linfo, ty, inf) = Core.Inference.typeinf(li, ti, env, true)
# get the code for it
return _dump_function(linfo, native, wrapper, strip_ir_metadata, dump_module)
end

function _dump_function(linfo::LambdaInfo, native::Bool, wrapper::Bool, strip_ir_metadata::Bool, dump_module::Bool)
if native
llvmf = ccall(:jl_get_llvmf_decl, Ptr{Void}, (Any, Bool), linfo, wrapper)
else
llvmf = ccall(:jl_get_llvmf_defn, Ptr{Void}, (Any, Bool), linfo, wrapper)
end
if llvmf == C_NULL
error("did not find a unique method for the specified argument types")
error("could not compile the specified method")
end

if native
str = ccall(:jl_dump_function_asm, Ref{String}, (Ptr{Void},Cint), llvmf, 0)
str = ccall(:jl_dump_function_asm, Ref{String}, (Ptr{Void}, Cint), llvmf, 0)
else
str = ccall(:jl_dump_function_ir, Ref{String},
(Ptr{Void}, Bool, Bool), llvmf, strip_ir_metadata, dump_module)
end

isleaftype(t) || (str = "# WARNING: This code may not match what actually runs.\n" * str)
# TODO: use jl_is_cacheable_sig instead of isleaftype
isleaftype(linfo.specTypes) || (str = "; WARNING: This code may not match what actually runs.\n" * str)
return str
end

Expand Down Expand Up @@ -450,11 +468,16 @@ function which(f::ANY, t::ANY)
return first(ms)
else
ft = isa(f,Type) ? Type{f} : typeof(f)
m = ccall(:jl_gf_invoke_lookup, Any, (Any,), Tuple{ft, t.parameters...})
tt = Tuple{ft, t.parameters...}
m = ccall(:jl_gf_invoke_lookup, Any, (Any,), tt)
if m === nothing
error("no method found for the specified argument types")
end
return m.func::Method
meth = m.func::Method
if ccall(:jl_has_call_ambiguities, Int32, (Any, Any), tt, meth) != 0
error("method match is ambiguous for the specified argument types")
end
return meth
end
end

Expand Down
2 changes: 1 addition & 1 deletion deps/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ CONFIGURE_COMMON += F77="$(FC)" CC="$(CC) $(DEPS_CFLAGS)" CXX="$(CXX) $(DEPS_CXX
CMAKE_CC_ARG := $(CC_ARG) $(DEPS_CFLAGS)
CMAKE_CXX_ARG := $(CXX_ARG) $(DEPS_CXXFLAGS)

CMAKE_COMMON := -DCMAKE_INSTALL_PREFIX:PATH=$(build_prefix) -DCMAKE_PREFIX_PATH=$(build_prefix)
CMAKE_COMMON := -DCMAKE_INSTALL_PREFIX:PATH=$(build_prefix) -DCMAKE_PREFIX_PATH=$(build_prefix) -DLIB_INSTALL_DIR=$(build_shlibdir)
ifneq ($(VERBOSE), 0)
CMAKE_COMMON += -DCMAKE_VERBOSE_MAKEFILE=ON
endif
Expand Down

This file was deleted.

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
4c91d4c9161555c911630b0a70ddec03
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
c53513a5aea84405bf302b084a23f24f54148aac90a2bd666219ce14879723baab959942934d0d801a4572fffd07e60a7d574ade8d7eb57b6da8216063c20a48
9 changes: 8 additions & 1 deletion deps/curl.mk
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,14 @@ $(SRCDIR)/srccache/curl-$(CURL_VER)/configure: $(SRCDIR)/srccache/curl-$(CURL_VE
$(BUILDDIR)/curl-$(CURL_VER)/config.status: $(SRCDIR)/srccache/curl-$(CURL_VER)/configure
mkdir -p $(dir $@)
cd $(dir $@) && \
$< $(CONFIGURE_COMMON) --includedir=$(build_includedir) --without-ssl --with-mbedtls=$(build_prefix) CFLAGS="$(CFLAGS) $(CURL_CFLAGS)" LDFLAGS="$(LDFLAGS) $(CURL_LDFLAGS)"
$< $(CONFIGURE_COMMON) --includedir=$(build_includedir) \
--without-ssl --without-gnutls --without-gssapi \
--without-libidn --without-libmetalink --without-librtmp \
--without-nghttp2 --without-nss --without-polarssl \
--without-spnego --disable-ares --disable-ldap \
--disable-ldaps --without-zsh-functions-dir \
--with-libssh2=$(build_prefix) --with-mbedtls=$(build_prefix) \
CFLAGS="$(CFLAGS) $(CURL_CFLAGS)" LDFLAGS="$(LDFLAGS) $(CURL_LDFLAGS)"
touch -c $@

$(CURL_SRC_TARGET): $(BUILDDIR)/curl-$(CURL_VER)/config.status
Expand Down
7 changes: 6 additions & 1 deletion deps/libgit2.mk
Original file line number Diff line number Diff line change
Expand Up @@ -47,9 +47,14 @@ ifeq ($(OS),Linux)
$(BUILDDIR)/$(LIBGIT2_SRC_DIR)/Makefile: $(SRCDIR)/srccache/$(LIBGIT2_SRC_DIR)/libgit2-require-openssl.patch-applied $(SRCDIR)/srccache/$(LIBGIT2_SRC_DIR)/libgit2-openssl-hang.patch-applied
endif
ifneq ($(OS),WINNT)
ifeq ($(USE_SYSTEM_CURL), 0)
$(BUILDDIR)/$(LIBGIT2_SRC_DIR)/Makefile: $(CURL_OBJ_TARGET)
endif
$(BUILDDIR)/$(LIBGIT2_SRC_DIR)/Makefile: $(SRCDIR)/srccache/$(LIBGIT2_SRC_DIR)/CMakeLists.txt $(SRCDIR)/srccache/$(LIBGIT2_SRC_DIR)/libgit2-ssh.patch-applied $(SRCDIR)/srccache/$(LIBGIT2_SRC_DIR)/libgit2-agent-nonfatal.patch-applied $(LIBSSH2_OBJ_TARGET)
endif
ifeq ($(USE_SYSTEM_LIBSSH2), 0)
$(BUILDDIR)/$(LIBGIT2_SRC_DIR)/Makefile: $(LIBSSH2_OBJ_TARGET)
endif
$(BUILDDIR)/$(LIBGIT2_SRC_DIR)/Makefile: $(SRCDIR)/srccache/$(LIBGIT2_SRC_DIR)/CMakeLists.txt $(SRCDIR)/srccache/$(LIBGIT2_SRC_DIR)/libgit2-ssh.patch-applied $(SRCDIR)/srccache/$(LIBGIT2_SRC_DIR)/libgit2-agent-nonfatal.patch-applied
mkdir -p $(dir $@)
cd $(dir $@) && \
$(CMAKE) $(dir $<) $(LIBGIT2_OPTS)
Expand Down
2 changes: 1 addition & 1 deletion deps/libssh2.mk
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ LIBSSH2_OBJ_SOURCE := $(BUILDDIR)/$(LIBSSH2_SRC_DIR)/src/libssh2.$(SHLIB_EXT)
LIBSSH2_OBJ_TARGET := $(build_shlibdir)/libssh2.$(SHLIB_EXT)

LIBSSH2_OPTS := $(CMAKE_COMMON) -DBUILD_SHARED_LIBS=ON -DBUILD_EXAMPLES=OFF \
-DCMAKE_BUILD_TYPE=Release -DCMAKE_INSTALL_LIBDIR=lib
-DCMAKE_BUILD_TYPE=Release

ifeq ($(OS),WINNT)
LIBSSH2_OPTS += -DCRYPTO_BACKEND=WinCNG -DENABLE_ZLIB_COMPRESSION=OFF
Expand Down
2 changes: 1 addition & 1 deletion deps/libuv.version
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
LIBUV_BRANCH=julia-uv1.9.0
LIBUV_SHA1=28743d6091531340cfe316de2b2d385fe1778ff5
LIBUV_SHA1=8d5131b6c1595920dd30644cd1435b4f344b46c8
1 change: 1 addition & 0 deletions doc/devdocs/C.rst
Original file line number Diff line number Diff line change
Expand Up @@ -12,3 +12,4 @@
backtraces
debuggingtips
valgrind
sanitizers
44 changes: 44 additions & 0 deletions doc/devdocs/sanitizers.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
*****************
Sanitizer support
*****************

General considerations
----------------------

Using Clang's sanitizers obviously require you to use Clang (``USECLANG=1``), but there's
another catch: most sanitizers require a run-time library, provided by the host compiler,
while the instrumented code generated by Julia's JIT relies on functionality from that
library. This implies that the LLVM version of your host compiler matches that of the LLVM
library used within Julia.

An easy solution is to have an dedicated build folder for providing a matching toolchain, by
building with ``BUILD_LLVM_CLANG=1`` and overriding ``LLVM_USE_CMAKE=1`` (Autotool-based
builds are incompatible with ASAN). You can then refer to this toolchain from another build
folder by specifying ``USECLANG=1`` while overriding the ``CC`` and ``CXX`` variables.


Address Sanitizer (ASAN)
------------------------

For detecting or debugging memory bugs, you can use Clang's `address sanitizer (ASAN)
<http://clang.llvm.org/docs/AddressSanitizer.html>`_. By compiling with
``SANITIZE=1`` you enable ASAN for the Julia compiler and its generated code. In addition,
you can specify ``LLVM_SANITIZE=1`` to sanitize the LLVM library as well. Note that these
options incur a high performance and memory cost. For example, using ASAN for Julia and LLVM
makes ``testall1`` takes 8-10 times as long while using 20 times as much memory (this can
be reduced to respectively a factor of 3 and 4 by using the options described below).

By default, Julia sets the ``allow_user_segv_handler=1`` ASAN flag, which is required for
signal delivery to work properly. You can define other options using the ``ASAN_OPTIONS``
environment flag, in which case you'll need to repeat the default option mentioned before.
For example, memory usage can be reduced by specifying ``fast_unwind_on_malloc=0`` and
``malloc_context_size=2``, at the cost of backtrace accuracy. For now, Julia also sets
``detect_leaks=0``, but this should be removed in the future.


Memory Sanitizer (MSAN)
-----------------------

For detecting use of uninitialized memory, you can use Clang's `memory sanitizer (MSAN)
<http://clang.llvm.org/docs/MemorySanitizer.html>`_ by compiling with
``SANITIZE_MEMORY=1``.
2 changes: 2 additions & 0 deletions doc/stdlib/libdl.rst
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@ The names in :mod:`Base.Libdl` are not exported and need to be called e.g. as ``

Load a shared library, returning an opaque handle.

The extension given by the constant ``dlext`` (``.so``\ , ``.dll``\ , or ``.dylib``\ ) can be omitted from the ``libfile`` string, as it is automatically appended if needed. If ``libfile`` is not an absolute path name, then the paths in the array ``DL_LOAD_PATH`` are searched for ``libfile``\ , followed by the system load path.

The optional flags argument is a bitwise-or of zero or more of ``RTLD_LOCAL``\ , ``RTLD_GLOBAL``\ , ``RTLD_LAZY``\ , ``RTLD_NOW``\ , ``RTLD_NODELETE``\ , ``RTLD_NOLOAD``\ , ``RTLD_DEEPBIND``\ , and ``RTLD_FIRST``\ . These are converted to the corresponding flags of the POSIX (and/or GNU libc and/or MacOS) dlopen command, if possible, or are ignored if the specified functionality is not available on the current platform. The default flags are platform specific. On MacOS the default ``dlopen`` flags are ``RTLD_LAZY|RTLD_DEEPBIND|RTLD_GLOBAL`` while on other platforms the defaults are ``RTLD_LAZY|RTLD_DEEPBIND|RTLD_LOCAL``\ . An important usage of these flags is to specify non default behavior for when the dynamic library loader binds library references to exported symbols and if the bound references are put into process local or global scope. For instance ``RTLD_LAZY|RTLD_DEEPBIND|RTLD_GLOBAL`` allows the library's symbols to be available for usage in other shared libraries, addressing situations where there are dependencies between shared libraries.

.. function:: dlopen_e(libfile::AbstractString [, flags::Integer])
Expand Down
40 changes: 29 additions & 11 deletions src/alloc.c
Original file line number Diff line number Diff line change
Expand Up @@ -264,6 +264,7 @@ JL_DLLEXPORT jl_value_t *jl_new_struct_uninit(jl_datatype_t *type)
return jv;
}


extern jl_value_t *jl_builtin_getfield;
jl_value_t *jl_resolve_globals(jl_value_t *expr, jl_lambda_info_t *lam)
{
Expand All @@ -280,20 +281,37 @@ jl_value_t *jl_resolve_globals(jl_value_t *expr, jl_lambda_info_t *lam)
e->head == boundscheck_sym || e->head == simdloop_sym) {
}
else {
if (e->head == call_sym && jl_expr_nargs(e) == 3 && jl_is_quotenode(jl_exprarg(e,2)) &&
if (e->head == call_sym && jl_expr_nargs(e) == 3 && jl_is_quotenode(jl_exprarg(e, 2)) &&
lam->def->module != NULL) {
// replace getfield(module_expr, :sym) with GlobalRef
jl_value_t *s = jl_fieldref(jl_exprarg(e,2),0);
jl_value_t *fe = jl_exprarg(e,0);
jl_value_t *s = jl_fieldref(jl_exprarg(e, 2), 0);
jl_value_t *fe = jl_exprarg(e, 0);
if (jl_is_symbol(s) && jl_is_globalref(fe)) {
jl_value_t *f = jl_static_eval(fe, NULL, lam->def->module, lam, 0, 0);
jl_binding_t *b = jl_get_binding(jl_globalref_mod(fe), jl_globalref_name(fe));
jl_value_t *f = NULL;
if (b && b->constp) {
f = b->value;
}
if (f == jl_builtin_getfield) {
jl_value_t *me = jl_exprarg(e,1);
if (jl_is_globalref(me) ||
(jl_is_symbol(me) && jl_binding_resolved_p(lam->def->module, (jl_sym_t*)me))) {
jl_value_t *m = jl_static_eval(me, NULL, lam->def->module, lam, 0, 0);
if (m && jl_is_module(m))
return jl_module_globalref((jl_module_t*)m, (jl_sym_t*)s);
jl_value_t *me = jl_exprarg(e, 1);
jl_module_t *me_mod = NULL;
jl_sym_t *me_sym = NULL;
if (jl_is_globalref(me)) {
me_mod = jl_globalref_mod(me);
me_sym = jl_globalref_name(me);
}
else if (jl_is_symbol(me) && jl_binding_resolved_p(lam->def->module, (jl_sym_t*)me)) {
me_mod = lam->def->module;
me_sym = (jl_sym_t*)me;
}
if (me_mod && me_sym) {
jl_binding_t *b = jl_get_binding(me_mod, me_sym);
if (b && b->constp) {
jl_value_t *m = b->value;
if (m && jl_is_module(m)) {
return jl_module_globalref((jl_module_t*)m, (jl_sym_t*)s);
}
}
}
}
}
Expand All @@ -303,7 +321,7 @@ jl_value_t *jl_resolve_globals(jl_value_t *expr, jl_lambda_info_t *lam)
e->head == bitstype_sym || e->head == module_sym)
i++;
for(; i < jl_array_len(e->args); i++) {
jl_exprargset(e, i, jl_resolve_globals(jl_exprarg(e,i), lam));
jl_exprargset(e, i, jl_resolve_globals(jl_exprarg(e, i), lam));
}
}
}
Expand Down
Loading