You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
237 lines
7.6 KiB
Java
237 lines
7.6 KiB
Java
8 years ago
|
/* -*- mode: java; c-basic-offset: 2; indent-tabs-mode: nil -*- */
|
||
|
|
||
|
/*
|
||
|
Part of the Processing project - http://processing.org
|
||
|
|
||
|
Copyright (c) 2011-12 Ben Fry and Casey Reas
|
||
|
|
||
|
This library is free software; you can redistribute it and/or
|
||
|
modify it under the terms of the GNU Lesser General Public
|
||
|
License as published by the Free Software Foundation; either
|
||
|
version 2.1 of the License, or (at your option) any later version.
|
||
|
|
||
|
This library is distributed in the hope that it will be useful,
|
||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||
|
Lesser General Public License for more details.
|
||
|
|
||
|
You should have received a copy of the GNU Lesser General
|
||
|
Public License along with this library; if not, write to the
|
||
|
Free Software Foundation, Inc., 59 Temple Place, Suite 330,
|
||
|
Boston, MA 02111-1307 USA
|
||
|
*/
|
||
|
|
||
|
package processing.video;
|
||
|
|
||
|
import java.util.HashMap;
|
||
|
import java.util.Map;
|
||
|
|
||
|
import com.sun.jna.Library;
|
||
|
import com.sun.jna.Native;
|
||
|
import com.sun.jna.Platform;
|
||
|
|
||
|
/**
|
||
|
* This class loads the gstreamer native libraries.
|
||
|
* By Andres Colubri
|
||
|
* Based on code by Tal Shalif
|
||
|
*
|
||
|
*/
|
||
|
public class LibraryLoader {
|
||
|
|
||
|
public interface DummyLibrary extends Library {
|
||
|
}
|
||
|
|
||
|
private static LibraryLoader instance;
|
||
|
|
||
|
static final Object[][] WINDOWS_DEPENDENCIES = {
|
||
|
// glib libraries
|
||
|
{ "gio-2.0", new String[] {}, true },
|
||
|
{ "glib-2.0", new String[] {}, true },
|
||
|
{ "gmodule-2.0", new String[] {}, true },
|
||
|
{ "gobject-2.0", new String[] {}, true },
|
||
|
{ "gthread-2.0", new String[] {}, true },
|
||
|
|
||
|
// Core gstreamer libraries
|
||
|
{ "gstapp-0.10", new String[] {}, true },
|
||
|
{ "gstaudio-0.10", new String[] {}, true },
|
||
|
{ "gstbase-0.10", new String[] {}, true },
|
||
|
{ "gstbasevideo-0.10", new String[] {}, true },
|
||
|
{ "gstcdda-0.10", new String[] {}, true },
|
||
|
{ "gstcontroller-0.10", new String[] {}, true },
|
||
|
{ "gstdataprotocol-0.10", new String[] {}, true },
|
||
|
{ "gstfft-0.10", new String[] {}, true },
|
||
|
{ "gstinterfaces-0.10", new String[] {}, true },
|
||
|
{ "gstnet-0.10", new String[] {}, true },
|
||
|
{ "gstnetbuffer-0.10", new String[] {}, true },
|
||
|
{ "gstpbutils-0.10", new String[] {}, true },
|
||
|
{ "gstphotography-0.10", new String[] {}, true },
|
||
|
{ "gstreamer-0.10", new String[] {}, true },
|
||
|
{ "gstriff-0.10", new String[] {}, true },
|
||
|
{ "gstrtp-0.10", new String[] {}, true },
|
||
|
{ "gstrtsp-0.10", new String[] {}, true },
|
||
|
{ "gstsdp-0.10", new String[] {}, true },
|
||
|
{ "gstsignalprocessor-0.10", new String[] {}, true },
|
||
|
{ "gsttag-0.10", new String[] {}, true },
|
||
|
{ "gstvideo-0.10", new String[] {}, true },
|
||
|
|
||
|
// External libraries
|
||
|
{ "libiconv-2", new String[] {}, false },
|
||
|
{ "libintl-8", new String[] {}, false },
|
||
|
{ "libjpeg-8", new String[] {}, false },
|
||
|
{ "libogg-0", new String[] {}, false },
|
||
|
{ "liborc-0.4-0", new String[] {}, false },
|
||
|
{ "liborc-test-0.4-0", new String[] {}, false },
|
||
|
{ "libpng14-14", new String[] {}, false },
|
||
|
{ "libtheora-0", new String[] {}, false },
|
||
|
{ "libtheoradec-1", new String[] {}, false },
|
||
|
{ "libtheoraenc-1", new String[] {}, false },
|
||
|
{ "libvorbis-0", new String[] {}, false },
|
||
|
{ "libvorbisenc-2", new String[] {}, false },
|
||
|
{ "libvorbisfile-3", new String[] {}, false },
|
||
|
{ "libxml2-2", new String[] {}, false },
|
||
|
{ "zlib1", new String[] {}, false } };
|
||
|
|
||
|
static final Object[][] MACOSX_DEPENDENCIES = {
|
||
|
{ "gstbase-0.10", new String[] { "gstreamer-0.10" }, true },
|
||
|
{ "gstinterfaces-0.10", new String[] { "gstreamer-0.10" }, true },
|
||
|
{ "gstcontroller-0.10", new String[] { "gstreamer-0.10" }, true },
|
||
|
{ "gstaudio-0.10", new String[] { "gstbase-0.10" }, true },
|
||
|
{ "gstvideo-0.10", new String[] { "gstbase-0.10" }, true } };
|
||
|
|
||
|
static final Object[][] DEFAULT_DEPENDENCIES = {
|
||
|
{ "gstreamer-0.10", new String[] {}, true },
|
||
|
{ "gstbase-0.10", new String[] { "gstreamer-0.10" }, true },
|
||
|
{ "gstinterfaces-0.10", new String[] { "gstreamer-0.10" }, true },
|
||
|
{ "gstcontroller-0.10", new String[] { "gstreamer-0.10" }, true },
|
||
|
{ "gstaudio-0.10", new String[] { "gstbase-0.10" }, true },
|
||
|
{ "gstvideo-0.10", new String[] { "gstbase-0.10" }, true }, };
|
||
|
|
||
|
|
||
|
static final Object[][] dependencies =
|
||
|
Platform.isWindows() ? WINDOWS_DEPENDENCIES :
|
||
|
Platform.isMac() ? MACOSX_DEPENDENCIES : DEFAULT_DEPENDENCIES;
|
||
|
|
||
|
|
||
|
private static final Map<String, Object> loadedMap =
|
||
|
new HashMap<String, Object>();
|
||
|
|
||
|
|
||
|
private static final int RECURSIVE_LOAD_MAX_DEPTH = 5;
|
||
|
|
||
|
|
||
|
private LibraryLoader() {
|
||
|
}
|
||
|
|
||
|
|
||
|
private void preLoadLibs() {
|
||
|
for (Object[] a : dependencies) {
|
||
|
load(a[0].toString(), DummyLibrary.class, true, 0, (Boolean) a[2]);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
|
||
|
private String[] findDeps(String name) {
|
||
|
|
||
|
for (Object[] a : dependencies) {
|
||
|
if (name.equals(a[0])) {
|
||
|
|
||
|
return (String[]) a[1];
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return new String[] {}; // library dependancy load chain unspecified -
|
||
|
// probably client call
|
||
|
}
|
||
|
|
||
|
|
||
|
public Object load(String name, Class<?> clazz, boolean reqLib) {
|
||
|
return load(name, clazz, true, 0, reqLib);
|
||
|
}
|
||
|
|
||
|
|
||
|
private Object load(String name, Class<?> clazz, boolean forceReload,
|
||
|
int depth, boolean reqLib) {
|
||
|
|
||
|
assert depth < RECURSIVE_LOAD_MAX_DEPTH : String.format(
|
||
|
"recursive max load depth %s has been exceeded", depth);
|
||
|
|
||
|
Object library = loadedMap.get(name);
|
||
|
|
||
|
if (null == library || forceReload) {
|
||
|
|
||
|
// Logger.getAnonymousLogger().info(String.format("%" + ((depth + 1) * 2)
|
||
|
// + "sloading %s", "->", name));
|
||
|
|
||
|
try {
|
||
|
String[] deps = findDeps(name);
|
||
|
|
||
|
for (String lib : deps) {
|
||
|
load(lib, DummyLibrary.class, false, depth + 1, reqLib);
|
||
|
}
|
||
|
|
||
|
library = loadLibrary(name, clazz, reqLib);
|
||
|
|
||
|
if (library != null) {
|
||
|
loadedMap.put(name, library);
|
||
|
}
|
||
|
} catch (Exception e) {
|
||
|
if (reqLib)
|
||
|
throw new RuntimeException(String.format(
|
||
|
"can not load required library %s", name, e));
|
||
|
else
|
||
|
System.out.println(String.format("can not load library %s", name, e));
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return library;
|
||
|
}
|
||
|
|
||
|
|
||
|
private static Object loadLibrary(String name, Class<?> clazz,
|
||
|
boolean reqLib) {
|
||
|
|
||
|
// Logger.getAnonymousLogger().info(String.format("loading %s", name));
|
||
|
|
||
|
String[] nameFormats;
|
||
|
nameFormats = Platform.isWindows() ? new String[] { "lib%s", "lib%s-0",
|
||
|
"%s" } : new String[] { "%s-0", "%s" };
|
||
|
|
||
|
UnsatisfiedLinkError linkError = null;
|
||
|
|
||
|
for (String fmt : nameFormats) {
|
||
|
try {
|
||
|
String s = String.format(fmt, name);
|
||
|
//System.out.println("Trying to load library file " + s);
|
||
|
Object obj = Native.loadLibrary(s, clazz);
|
||
|
//System.out.println("Loaded library " + s + " succesfully!");
|
||
|
return obj;
|
||
|
} catch (UnsatisfiedLinkError ex) {
|
||
|
linkError = ex;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if (reqLib)
|
||
|
throw new UnsatisfiedLinkError(
|
||
|
String.format(
|
||
|
"can't load library %s (%1$s|lib%1$s|lib%1$s-0) with " +
|
||
|
"-Djna.library.path=%s. Last error:%s",
|
||
|
name, System.getProperty("jna.library.path"), linkError));
|
||
|
else {
|
||
|
System.out.println(String.format(
|
||
|
"can't load library %s (%1$s|lib%1$s|lib%1$s-0) with " +
|
||
|
"-Djna.library.path=%s. Last error:%s",
|
||
|
name, System.getProperty("jna.library.path"), linkError));
|
||
|
return null;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
|
||
|
public static synchronized LibraryLoader getInstance() {
|
||
|
if (null == instance) {
|
||
|
instance = new LibraryLoader();
|
||
|
instance.preLoadLibs();
|
||
|
}
|
||
|
return instance;
|
||
|
}
|
||
|
}
|