]> gitweb.factorcode.org Git - factor.git/commitdiff
alien.libraries.finder: split into sub-vocabularies and implement macosx better.
authorJohn Benediktsson <mrjbq7@gmail.com>
Sat, 16 Nov 2013 19:58:37 +0000 (11:58 -0800)
committerJohn Benediktsson <mrjbq7@gmail.com>
Sat, 16 Nov 2013 19:58:37 +0000 (11:58 -0800)
basis/alien/libraries/finder/finder.factor
basis/alien/libraries/finder/linux/linux.factor [new file with mode: 0644]
basis/alien/libraries/finder/macosx/macosx-tests.factor [new file with mode: 0644]
basis/alien/libraries/finder/macosx/macosx.factor [new file with mode: 0644]
basis/alien/libraries/finder/windows/windows.factor [new file with mode: 0644]

index 24f86b390408b68b08285d3c42e6830bf87ef38b..574e00ad4bbae7d5be7d35afbb7156fc5490c236 100644 (file)
@@ -1,57 +1,12 @@
-USING:
-    alien.libraries
-    arrays
-    assocs
-    combinators
-    formatting
-    io io.encodings.utf8 io.launcher io.pathnames
-    kernel
-    sequences
-    splitting
-    system ;
-IN: alien.libraries.finder
-
-! Util
-: vsprintf1 ( obj fmt -- str )
-    [ 1array ] dip vsprintf ;
-
-CONSTANT: name-formats {
-    { windows { "%s.dll" "lib%s.dll" } }
-    { linux { "lib%s.so" } }
-    { unix { "lib%s.so" } }
-    { macosx { "lib%s.dylib" } }
-}
-
-! On Windows, bundled dlls are shipped in a directory named "dlls" in
-! the Factor distribution. On other operating systems, the dynamic
-! linker can itself figure out where libraries are located.
-: path-formats ( -- path-formats )
-    { "" } os windows? [ "dlls" suffix ] when name-formats os of
-    [ append-path ] cartesian-map concat ;
 
-! Find lib using ldconfig
-CONSTANT: mach-map {
-    { ppc.64 "libc6,64bit" }
-    { x86.32 "libc6,x86-32" }
-    { x86.64 "libc6,x86-64" }
-}
+USING: combinators system vocabs ;
 
-: ldconfig-cache ( -- seq )
-    "/sbin/ldconfig -p" utf8 [ lines ] with-process-reader rest
-    [ "=>" "" replace "\t " split harvest ] map ;
-
-: ldconfig-filter ( -- str )
-    mach-map cpu of dup "libc6" ? "(" ")" surround ;
-
-: ldconfig-matches? ( lib this-lib this-arch -- ? )
-    [ start 0 = ] [ ldconfig-filter = ] bi* and ;
-
-: ldconfig-find-soname ( lib -- seq )
-    ldconfig-cache [ first2 ldconfig-matches? ] with filter [ first ] map ;
+IN: alien.libraries.finder
 
-: candidate-paths ( name -- paths )
-    path-formats [ vsprintf1 ] with map
-    os [ unix? ] [ linux? ] bi or [ first ldconfig-find-soname ] when ;
+HOOK: find-library os ( name -- path/f )
 
-: find-library ( name -- path/f )
-    candidate-paths [ dlopen dll-valid? ] map-find nip ;
+{
+    { [ os macosx?  ] [ "alien.libraries.finder.macosx"  ] }
+    { [ os linux?   ] [ "alien.libraries.finder.linux"   ] }
+    { [ os windows? ] [ "alien.libraries.finder.windows" ] }
+} cond require
diff --git a/basis/alien/libraries/finder/linux/linux.factor b/basis/alien/libraries/finder/linux/linux.factor
new file mode 100644 (file)
index 0000000..97c8e1c
--- /dev/null
@@ -0,0 +1,36 @@
+! Copyright (C) 2013 Björn Lindqvist
+! See http://factorcode.org/license.txt for BSD license
+
+USING: alien.libraries alien.libraries.finder assocs io
+io.encodings.utf8 io.launcher kernel sequences splitting system
+;
+
+IN: alien.libraries.finder.linux
+
+<PRIVATE
+
+CONSTANT: mach-map {
+    { ppc.64 "libc6,64bit" }
+    { x86.32 "libc6,x86-32" }
+    { x86.64 "libc6,x86-64" }
+}
+
+: ldconfig-cache ( -- seq )
+    "/sbin/ldconfig -p" utf8 [ lines ] with-process-reader rest
+    [ "=>" "" replace "\t " split harvest ] map ;
+
+: ldconfig-filter ( -- str )
+    mach-map cpu of "libc6" or "(" ")" surround ;
+
+: ldconfig-matches? ( lib this-lib this-arch -- ? )
+    [ start 0 = ] [ ldconfig-filter = ] bi* and ;
+
+: ldconfig-find-soname ( lib -- seq )
+    ldconfig-cache [ first2 ldconfig-matches? ] with filter [ first ] map ;
+
+PRIVATE>
+
+M: linux find-library
+    "lib" ".so" surround ldconfig-find-soname
+    [ dlopen dll-valid? ] map-find nip ;
+
diff --git a/basis/alien/libraries/finder/macosx/macosx-tests.factor b/basis/alien/libraries/finder/macosx/macosx-tests.factor
new file mode 100644 (file)
index 0000000..6388eb5
--- /dev/null
@@ -0,0 +1,44 @@
+
+USING: sequences tools.test ;
+
+IN: alien.libraries.finder.macosx
+
+{
+    {
+        f
+        f
+        f
+        f
+        T{ framework-info f "Location" "Name.framework/Name" "Name" f f }
+        T{ framework-info f "Location" "Name.framework/Name_suffix" "Name" f "suffix" }
+        f
+        f
+        T{ framework-info f "Location" "Name.framework/Versions/A/Name" "Name" "A" f }
+        T{ framework-info f "Location" "Name.framework/Versions/A/Name_suffix" "Name" "A" "suffix" }
+    }
+} [
+    {
+        "broken/path"
+        "broken/path/_suffix"
+        "Location/Name.framework"
+        "Location/Name.framework/_suffix"
+        "Location/Name.framework/Name"
+        "Location/Name.framework/Name_suffix"
+        "Location/Name.framework/Versions"
+        "Location/Name.framework/Versions/A"
+        "Location/Name.framework/Versions/A/Name"
+        "Location/Name.framework/Versions/A/Name_suffix"
+    } [ <framework-info> ] map
+] unit-test
+
+{
+    {
+        "/usr/lib/libSystem.dylib"
+        "/System/Library/Frameworks/System.framework/System"
+    }
+} [
+    {
+        "libSystem.dylib"
+        "System.framework/System"
+    } [ dyld-find ] map
+] unit-test
diff --git a/basis/alien/libraries/finder/macosx/macosx.factor b/basis/alien/libraries/finder/macosx/macosx.factor
new file mode 100644 (file)
index 0000000..63da9a3
--- /dev/null
@@ -0,0 +1,135 @@
+! Copyright (C) 2013 John Benediktsson
+! See http://factorcode.org/license.txt for BSD license
+
+USING: accessors alien.libraries.finder arrays assocs
+combinators.short-circuit environment io.files io.files.info
+io.pathnames kernel locals make namespaces sequences splitting
+system ;
+
+IN: alien.libraries.finder.macosx
+
+<PRIVATE
+
+TUPLE: framework-info location name shortname version suffix ;
+
+: make-framework-info ( filename -- info/f )
+    [ framework-info new ] dip
+    "/" split dup [ ".framework" tail? ] find drop [
+        cut [
+            [ "/" join ] bi@ [ >>location ] [ >>name ] bi*
+        ] keep [
+            rest dup ?first "Versions" = [
+                rest dup empty? [
+                    unclip swap [ >>version ] dip
+                ] unless
+            ] when ?first "_" split1 [ >>shortname ] [ >>suffix ] bi*
+        ] unless-empty
+    ] [ drop ] if* dup shortname>> empty? [ drop f ] when ;
+
+CONSTANT: default-framework-fallback {
+    "~/Library/Frameworks"
+    "/Library/Frameworks"
+    "/Network/Library/Frameworks"
+    "/System/Library/Frameworks"
+}
+
+CONSTANT: default-library-fallback {
+    "~/lib"
+    "/usr/local/lib"
+    "/lib"
+    "/usr/lib"
+}
+
+SYMBOL: dyld-environment
+
+: dyld-env ( name -- seq )
+    dyld-environment get [ at ] [ os-env ] if* ;
+
+: dyld-paths ( name -- seq )
+    dyld-env [ ":" split ] [ f ] if* ;
+
+: paths% ( name seq -- )
+    [ prepend-path , ] with each ;
+
+: dyld-override-search ( name -- seq )
+    [
+        dup make-framework-info [
+            name>> "DYLD_FRAMEWORK_PATH" dyld-paths paths%
+        ] when*
+
+        file-name "DYLD_LIBRARY_PATH" dyld-paths paths%
+    ] { } make ;
+
+SYMBOL: dyld-executable-path
+
+: dyld-executable-path-search ( name -- seq )
+    "@executable_path/" ?head dyld-executable-path get and [
+        dyld-executable-path get prepend-path
+    ] [
+        drop f
+    ] if ;
+
+:: dyld-default-search ( name -- seq )
+    name make-framework-info :> framework
+    name file-name :> basename
+    "DYLD_FALLBACK_FRAMEWORK_PATH" dyld-paths :> fallback-framework-path
+    "DYLD_FALLBACK_LIBRARY_PATH" dyld-paths :> fallback-library-path
+    [
+        name ,
+
+        framework [
+            name>> fallback-framework-path paths%
+        ] when*
+
+        basename fallback-library-path paths%
+
+        framework fallback-framework-path empty? and [
+            framework name>> default-framework-fallback paths%
+        ] when
+
+        fallback-library-path empty? [
+            basename default-library-fallback paths%
+        ] when
+    ] { } make ;
+
+: dyld-image-suffix-search ( seq -- str )
+    "DYLD_IMAGE_SUFFIX" dyld-env [
+        swap [
+            [
+                [
+                    ".dylib" ?tail [ prepend ] dip
+                    [ ".dylib" append ] when ,
+                ] [
+                    ,
+                ] bi
+            ] with each
+        ] { } make
+    ] when* ;
+
+: dyld-search-paths ( name -- paths )
+    [ dyld-override-search ]
+    [ dyld-executable-path-search ]
+    [ dyld-default-search ] tri 3append
+    dyld-image-suffix-search ;
+
+PRIVATE>
+
+: dyld-find ( name -- path/f )
+    dyld-search-paths
+    [ { [ exists? ] [ file-info regular-file? ] } 1&& ] find
+    [ nip ] when* ;
+
+: framework-find ( name -- path )
+    dup dyld-find [ nip ] [
+        ".framework" over start [
+            dupd head
+        ] [
+            [ ".framework" append ] keep
+        ] if* file-name append-path dyld-find
+    ] if* ;
+
+M: macosx find-library
+    [ "lib" ".dylib" surround ]
+    [ ".dylib" append ]
+    [ ".framework/" over 3append ] tri 3array
+    [ dyld-find ] map-find drop ;
diff --git a/basis/alien/libraries/finder/windows/windows.factor b/basis/alien/libraries/finder/windows/windows.factor
new file mode 100644 (file)
index 0000000..cef5b54
--- /dev/null
@@ -0,0 +1,22 @@
+! Copyright (C) 2013 Björn Lindqvist
+! See http://factorcode.org/license.txt for BSD license
+
+USING: alien.libraries alien.libraries.finder arrays combinators
+kernel sequences system ;
+
+IN: alien.libraries.finder.windows
+
+<PRIVATE
+
+: candidate-paths ( name -- paths )
+    {
+        [ ".dll" append ]
+        [ "lib" ".dll" surround ]
+        [ "dlls/" ".dll" surround ]
+        [ "dlls/lib" ".dll" surround ]
+    } cleave 4array ;
+
+PRIVATE>
+
+M: windows find-library
+    candidate-paths [ dlopen dll-valid? ] map-find nip ;