2015-05-22 7 views
15

У меня есть проект, который использует библиотеку JOCL (http://www.jocl.org/) и имеет несколько модулей. Когда я бегу «тест ./activator» из командной строки или выполнить команду „тест“ в SBT консоли я получаю сообщение об ошибке, как следующее:«UnsatisfiedLinkError: родная библиотека, уже загруженная в другой загрузчик классов» в проекте с несколькими модулями

[info] Exception encountered when attempting to run a suite with class name: pl.tarsa.sortalgobox.opencl.CpuMergeSortSpec *** ABORTED *** 
[info] java.lang.UnsatisfiedLinkError: Error while loading native library "JOCL_0_1_9-linux-x86_64" with base name "JOCL_0_1_9" 
[info] Operating system name: Linux 
[info] Architecture   : amd64 
[info] Architecture bit size: 64 
[info] ---(start of nested stack traces)--- 
[info] Stack trace from the attempt to load the library as a file: 
[info] java.lang.UnsatisfiedLinkError: no JOCL_0_1_9-linux-x86_64 in java.library.path 
[info] at java.lang.ClassLoader.loadLibrary(ClassLoader.java:1865) 
[info] at java.lang.Runtime.loadLibrary0(Runtime.java:870) 
[info] at java.lang.System.loadLibrary(System.java:1122) 
[info] at org.jocl.LibUtils.loadLibrary(LibUtils.java:80) 
[info] at org.jocl.CL.<clinit>(CL.java:47) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextDescription$.enumerate(CLContextDescription.scala:44) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsManager$.contextsDescriptions$lzycompute(CLContextsManager.scala:6) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsManager$.contextsDescriptions(CLContextsManager.scala:6) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsManager$.createCpuContext(CLContextsManager.scala:9) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsCache$.cpuContext$lzycompute(CLContextsCache.scala:24) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsCache$.cpuContext(CLContextsCache.scala:24) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsCache$.withCpuContext(CLContextsCache.scala:28) 
[info] at pl.tarsa.sortalgobox.opencl.common.CpuSort.sort(CpuSort.scala:34) 
[info] at pl.tarsa.sortalgobox.opencl.common.CpuSort.sort(CpuSort.scala:32) 
[info] at pl.tarsa.sortalgobox.sorts.SortChecker.forEmptyArray(SortChecker.scala:31) 
[info] at pl.tarsa.sortalgobox.opencl.CpuMergeSortSpec$$anonfun$1$$anonfun$apply$mcV$sp$1.apply$mcV$sp(CpuMergeSortSpec.scala:32) 
[info] at pl.tarsa.sortalgobox.tests.CommonUnitSpecBase.guardedOpenCLTest(CommonUnitSpecBase.scala:40) 
[info] at pl.tarsa.sortalgobox.opencl.CpuMergeSortSpec$$anonfun$1.apply$mcV$sp(CpuMergeSortSpec.scala:31) 
[info] at pl.tarsa.sortalgobox.opencl.CpuMergeSortSpec$$anonfun$1.apply(CpuMergeSortSpec.scala:31) 
[info] at pl.tarsa.sortalgobox.opencl.CpuMergeSortSpec$$anonfun$1.apply(CpuMergeSortSpec.scala:31) 
[info] at org.scalatest.Transformer$$anonfun$apply$1.apply$mcV$sp(Transformer.scala:22) 
[info] at org.scalatest.OutcomeOf$class.outcomeOf(OutcomeOf.scala:85) 
[info] at org.scalatest.OutcomeOf$.outcomeOf(OutcomeOf.scala:104) 
[info] at org.scalatest.Transformer.apply(Transformer.scala:22) 
[info] at org.scalatest.Transformer.apply(Transformer.scala:20) 
[info] at org.scalatest.FlatSpecLike$$anon$1.apply(FlatSpecLike.scala:1647) 
[info] at org.scalamock.scalatest.AbstractMockFactory$$anonfun$withFixture$1.apply(AbstractMockFactory.scala:35) 
[info] at org.scalamock.scalatest.AbstractMockFactory$$anonfun$withFixture$1.apply(AbstractMockFactory.scala:34) 
[info] at org.scalamock.MockFactoryBase$class.withExpectations(MockFactoryBase.scala:41) 
[info] at pl.tarsa.sortalgobox.tests.CommonUnitSpecBase.withExpectations(CommonUnitSpecBase.scala:28) 
[info] at org.scalamock.scalatest.AbstractMockFactory$class.withFixture(AbstractMockFactory.scala:34) 
[info] at pl.tarsa.sortalgobox.tests.CommonUnitSpecBase.withFixture(CommonUnitSpecBase.scala:28) 
[info] at org.scalatest.FlatSpecLike$class.invokeWithFixture$1(FlatSpecLike.scala:1644) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTest$1.apply(FlatSpecLike.scala:1656) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTest$1.apply(FlatSpecLike.scala:1656) 
[info] at org.scalatest.SuperEngine.runTestImpl(Engine.scala:306) 
[info] at org.scalatest.FlatSpecLike$class.runTest(FlatSpecLike.scala:1656) 
[info] at org.scalatest.FlatSpec.runTest(FlatSpec.scala:1683) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTests$1.apply(FlatSpecLike.scala:1714) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTests$1.apply(FlatSpecLike.scala:1714) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:413) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:401) 
[info] at scala.collection.immutable.List.foreach(List.scala:381) 
[info] at org.scalatest.SuperEngine.traverseSubNodes$1(Engine.scala:401) 
[info] at org.scalatest.SuperEngine.org$scalatest$SuperEngine$$runTestsInBranch(Engine.scala:390) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:427) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:401) 
[info] at scala.collection.immutable.List.foreach(List.scala:381) 
[info] at org.scalatest.SuperEngine.traverseSubNodes$1(Engine.scala:401) 
[info] at org.scalatest.SuperEngine.org$scalatest$SuperEngine$$runTestsInBranch(Engine.scala:396) 
[info] at org.scalatest.SuperEngine.runTestsImpl(Engine.scala:483) 
[info] at org.scalatest.FlatSpecLike$class.runTests(FlatSpecLike.scala:1714) 
[info] at org.scalatest.FlatSpec.runTests(FlatSpec.scala:1683) 
[info] at org.scalatest.Suite$class.run(Suite.scala:1424) 
[info] at org.scalatest.FlatSpec.org$scalatest$FlatSpecLike$$super$run(FlatSpec.scala:1683) 
[info] at org.scalatest.FlatSpecLike$$anonfun$run$1.apply(FlatSpecLike.scala:1760) 
[info] at org.scalatest.FlatSpecLike$$anonfun$run$1.apply(FlatSpecLike.scala:1760) 
[info] at org.scalatest.SuperEngine.runImpl(Engine.scala:545) 
[info] at org.scalatest.FlatSpecLike$class.run(FlatSpecLike.scala:1760) 
[info] at org.scalatest.FlatSpec.run(FlatSpec.scala:1683) 
[info] at org.scalatest.tools.Framework.org$scalatest$tools$Framework$$runSuite(Framework.scala:462) 
[info] at org.scalatest.tools.Framework$ScalaTestTask.execute(Framework.scala:671) 
[info] at sbt.TestRunner.runTest$1(TestFramework.scala:76) 
[info] at sbt.TestRunner.run(TestFramework.scala:85) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1$$anonfun$apply$8.apply(TestFramework.scala:202) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1$$anonfun$apply$8.apply(TestFramework.scala:202) 
[info] at sbt.TestFramework$.sbt$TestFramework$$withContextLoader(TestFramework.scala:185) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1.apply(TestFramework.scala:202) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1.apply(TestFramework.scala:202) 
[info] at sbt.TestFunction.apply(TestFramework.scala:207) 
[info] at sbt.Tests$$anonfun$9.apply(Tests.scala:216) 
[info] at sbt.Tests$$anonfun$9.apply(Tests.scala:216) 
[info] at sbt.std.Transform$$anon$3$$anonfun$apply$2.apply(System.scala:44) 
[info] at sbt.std.Transform$$anon$3$$anonfun$apply$2.apply(System.scala:44) 
[info] at sbt.std.Transform$$anon$4.work(System.scala:63) 
[info] at sbt.Execute$$anonfun$submit$1$$anonfun$apply$1.apply(Execute.scala:226) 
[info] at sbt.Execute$$anonfun$submit$1$$anonfun$apply$1.apply(Execute.scala:226) 
[info] at sbt.ErrorHandling$.wideConvert(ErrorHandling.scala:17) 
[info] at sbt.Execute.work(Execute.scala:235) 
[info] at sbt.Execute$$anonfun$submit$1.apply(Execute.scala:226) 
[info] at sbt.Execute$$anonfun$submit$1.apply(Execute.scala:226) 
[info] at sbt.ConcurrentRestrictions$$anon$4$$anonfun$1.apply(ConcurrentRestrictions.scala:159) 
[info] at sbt.CompletionService$$anon$2.call(CompletionService.scala:28) 
[info] at java.util.concurrent.FutureTask.run(FutureTask.java:266) 
[info] at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) 
[info] at java.util.concurrent.FutureTask.run(FutureTask.java:266) 
[info] at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) 
[info] at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) 
[info] at java.lang.Thread.run(Thread.java:745) 
[info] Stack trace from the attempt to load the library as a resource: 
[info] java.lang.UnsatisfiedLinkError: Native Library /tmp/libJOCL_0_1_9-linux-x86_64.so already loaded in another classloader 
[info] at java.lang.ClassLoader.loadLibrary0(ClassLoader.java:1903) 
[info] at java.lang.ClassLoader.loadLibrary(ClassLoader.java:1822) 
[info] at java.lang.Runtime.load0(Runtime.java:809) 
[info] at java.lang.System.load(System.java:1086) 
[info] at org.jocl.LibUtils.loadLibraryResource(LibUtils.java:188) 
[info] at org.jocl.LibUtils.loadLibrary(LibUtils.java:91) 
[info] at org.jocl.CL.<clinit>(CL.java:47) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextDescription$.enumerate(CLContextDescription.scala:44) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsManager$.contextsDescriptions$lzycompute(CLContextsManager.scala:6) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsManager$.contextsDescriptions(CLContextsManager.scala:6) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsManager$.createCpuContext(CLContextsManager.scala:9) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsCache$.cpuContext$lzycompute(CLContextsCache.scala:24) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsCache$.cpuContext(CLContextsCache.scala:24) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsCache$.withCpuContext(CLContextsCache.scala:28) 
[info] at pl.tarsa.sortalgobox.opencl.common.CpuSort.sort(CpuSort.scala:34) 
[info] at pl.tarsa.sortalgobox.opencl.common.CpuSort.sort(CpuSort.scala:32) 
[info] at pl.tarsa.sortalgobox.sorts.SortChecker.forEmptyArray(SortChecker.scala:31) 
[info] at pl.tarsa.sortalgobox.opencl.CpuMergeSortSpec$$anonfun$1$$anonfun$apply$mcV$sp$1.apply$mcV$sp(CpuMergeSortSpec.scala:32) 
[info] at pl.tarsa.sortalgobox.tests.CommonUnitSpecBase.guardedOpenCLTest(CommonUnitSpecBase.scala:40) 
[info] at pl.tarsa.sortalgobox.opencl.CpuMergeSortSpec$$anonfun$1.apply$mcV$sp(CpuMergeSortSpec.scala:31) 
[info] at pl.tarsa.sortalgobox.opencl.CpuMergeSortSpec$$anonfun$1.apply(CpuMergeSortSpec.scala:31) 
[info] at pl.tarsa.sortalgobox.opencl.CpuMergeSortSpec$$anonfun$1.apply(CpuMergeSortSpec.scala:31) 
[info] at org.scalatest.Transformer$$anonfun$apply$1.apply$mcV$sp(Transformer.scala:22) 
[info] at org.scalatest.OutcomeOf$class.outcomeOf(OutcomeOf.scala:85) 
[info] at org.scalatest.OutcomeOf$.outcomeOf(OutcomeOf.scala:104) 
[info] at org.scalatest.Transformer.apply(Transformer.scala:22) 
[info] at org.scalatest.Transformer.apply(Transformer.scala:20) 
[info] at org.scalatest.FlatSpecLike$$anon$1.apply(FlatSpecLike.scala:1647) 
[info] at org.scalamock.scalatest.AbstractMockFactory$$anonfun$withFixture$1.apply(AbstractMockFactory.scala:35) 
[info] at org.scalamock.scalatest.AbstractMockFactory$$anonfun$withFixture$1.apply(AbstractMockFactory.scala:34) 
[info] at org.scalamock.MockFactoryBase$class.withExpectations(MockFactoryBase.scala:41) 
[info] at pl.tarsa.sortalgobox.tests.CommonUnitSpecBase.withExpectations(CommonUnitSpecBase.scala:28) 
[info] at org.scalamock.scalatest.AbstractMockFactory$class.withFixture(AbstractMockFactory.scala:34) 
[info] at pl.tarsa.sortalgobox.tests.CommonUnitSpecBase.withFixture(CommonUnitSpecBase.scala:28) 
[info] at org.scalatest.FlatSpecLike$class.invokeWithFixture$1(FlatSpecLike.scala:1644) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTest$1.apply(FlatSpecLike.scala:1656) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTest$1.apply(FlatSpecLike.scala:1656) 
[info] at org.scalatest.SuperEngine.runTestImpl(Engine.scala:306) 
[info] at org.scalatest.FlatSpecLike$class.runTest(FlatSpecLike.scala:1656) 
[info] at org.scalatest.FlatSpec.runTest(FlatSpec.scala:1683) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTests$1.apply(FlatSpecLike.scala:1714) 
[info] at org.scalatest.FlatSpecLike$$anonfun$runTests$1.apply(FlatSpecLike.scala:1714) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:413) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:401) 
[info] at scala.collection.immutable.List.foreach(List.scala:381) 
[info] at org.scalatest.SuperEngine.traverseSubNodes$1(Engine.scala:401) 
[info] at org.scalatest.SuperEngine.org$scalatest$SuperEngine$$runTestsInBranch(Engine.scala:390) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:427) 
[info] at org.scalatest.SuperEngine$$anonfun$traverseSubNodes$1$1.apply(Engine.scala:401) 
[info] at scala.collection.immutable.List.foreach(List.scala:381) 
[info] at org.scalatest.SuperEngine.traverseSubNodes$1(Engine.scala:401) 
[info] at org.scalatest.SuperEngine.org$scalatest$SuperEngine$$runTestsInBranch(Engine.scala:396) 
[info] at org.scalatest.SuperEngine.runTestsImpl(Engine.scala:483) 
[info] at org.scalatest.FlatSpecLike$class.runTests(FlatSpecLike.scala:1714) 
[info] at org.scalatest.FlatSpec.runTests(FlatSpec.scala:1683) 
[info] at org.scalatest.Suite$class.run(Suite.scala:1424) 
[info] at org.scalatest.FlatSpec.org$scalatest$FlatSpecLike$$super$run(FlatSpec.scala:1683) 
[info] at org.scalatest.FlatSpecLike$$anonfun$run$1.apply(FlatSpecLike.scala:1760) 
[info] at org.scalatest.FlatSpecLike$$anonfun$run$1.apply(FlatSpecLike.scala:1760) 
[info] at org.scalatest.SuperEngine.runImpl(Engine.scala:545) 
[info] at org.scalatest.FlatSpecLike$class.run(FlatSpecLike.scala:1760) 
[info] at org.scalatest.FlatSpec.run(FlatSpec.scala:1683) 
[info] at org.scalatest.tools.Framework.org$scalatest$tools$Framework$$runSuite(Framework.scala:462) 
[info] at org.scalatest.tools.Framework$ScalaTestTask.execute(Framework.scala:671) 
[info] at sbt.TestRunner.runTest$1(TestFramework.scala:76) 
[info] at sbt.TestRunner.run(TestFramework.scala:85) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1$$anonfun$apply$8.apply(TestFramework.scala:202) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1$$anonfun$apply$8.apply(TestFramework.scala:202) 
[info] at sbt.TestFramework$.sbt$TestFramework$$withContextLoader(TestFramework.scala:185) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1.apply(TestFramework.scala:202) 
[info] at sbt.TestFramework$$anon$2$$anonfun$$init$$1.apply(TestFramework.scala:202) 
[info] at sbt.TestFunction.apply(TestFramework.scala:207) 
[info] at sbt.Tests$$anonfun$9.apply(Tests.scala:216) 
[info] at sbt.Tests$$anonfun$9.apply(Tests.scala:216) 
[info] at sbt.std.Transform$$anon$3$$anonfun$apply$2.apply(System.scala:44) 
[info] at sbt.std.Transform$$anon$3$$anonfun$apply$2.apply(System.scala:44) 
[info] at sbt.std.Transform$$anon$4.work(System.scala:63) 
[info] at sbt.Execute$$anonfun$submit$1$$anonfun$apply$1.apply(Execute.scala:226) 
[info] at sbt.Execute$$anonfun$submit$1$$anonfun$apply$1.apply(Execute.scala:226) 
[info] at sbt.ErrorHandling$.wideConvert(ErrorHandling.scala:17) 
[info] at sbt.Execute.work(Execute.scala:235) 
[info] at sbt.Execute$$anonfun$submit$1.apply(Execute.scala:226) 
[info] at sbt.Execute$$anonfun$submit$1.apply(Execute.scala:226) 
[info] at sbt.ConcurrentRestrictions$$anon$4$$anonfun$1.apply(ConcurrentRestrictions.scala:159) 
[info] at sbt.CompletionService$$anon$2.call(CompletionService.scala:28) 
[info] at java.util.concurrent.FutureTask.run(FutureTask.java:266) 
[info] at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) 
[info] at java.util.concurrent.FutureTask.run(FutureTask.java:266) 
[info] at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) 
[info] at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) 
[info] at java.lang.Thread.run(Thread.java:745) 
[info] ---(end of nested stack traces)--- 
[info] at org.jocl.LibUtils.loadLibrary(LibUtils.java:122) 
[info] at org.jocl.CL.<clinit>(CL.java:47) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextDescription$.enumerate(CLContextDescription.scala:44) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsManager$.contextsDescriptions$lzycompute(CLContextsManager.scala:6) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsManager$.contextsDescriptions(CLContextsManager.scala:6) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsManager$.createCpuContext(CLContextsManager.scala:9) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsCache$.cpuContext$lzycompute(CLContextsCache.scala:24) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsCache$.cpuContext(CLContextsCache.scala:24) 
[info] at pl.tarsa.sortalgobox.opencl.common.CLContextsCache$.withCpuContext(CLContextsCache.scala:28) 
[info] at pl.tarsa.sortalgobox.opencl.common.CpuSort.sort(CpuSort.scala:34) 

Эти ошибки не появляются для испытаний в первом модуле/подпроект в зависимости от JOCL. Т.е. когда я делаю «./activator test», тогда тесты OpenCL из некоторого (первого протестированного) модуля работают, а все остальные - нет. Когда я делаю «./activator», чтобы запустить консоль SBT, а затем запускать «тест» несколько раз, а затем он ведет себя как обычный «./activator test», но для следующего теста все тесты OpenCL не работают с UnsatisfiedLinkError.

Вот мой файл сборка: https://github.com/tarsa/SortAlgoBox/blob/4a041d93beb572a6dcce100780bc675d46d814f3/project/MainBuild.scala

Согласно этому ответу: https://stackoverflow.com/a/23157190/492749 SBT использует магические загрузчик классов и переименовывает собственные библиотеки для каждых такого загрузчика классов. Проблема в том, что JOCL распаковывает собственные библиотеки во время загрузки какого-либо Java-класса, и результирующее имя файла и местоположение всегда одно и то же. Другими словами: магию SBT не хорошо сочетается с магией JOCL.

Какое у вас решение?

PS: тесты хорошо работают при исполнении IntelliJ IDEA - возможно, IDEA не использует магию загрузчика классов.

+0

Это * может * быть связано, но я не уверен: https://github.com/sbt/sbt-assembly/issues/141 – Marco13

+1

Примечание: для JOCL, в частности, будет обходной путь в версия 0.2.0: при запуске с 'java -DuniqueLibraryNames = true TheApplication' каждый раз будет генерировать новое имя библиотеки. Это может иметь нежелательные побочные эффекты и действительно должно рассматриваться только как * обходное решение *, пока не будет найдено правильное решение для общей проблемы с SBT/native library. – Marco13

ответ

1

According to this answer: https://stackoverflow.com/a/23157190/492749 SBT uses some magic classloaders and renames native libraries for each such classloader. The problem is that JOCL unpacks the native libraries during loading of some Java class and the resulting filename and location is always the same. In other words: SBT's magic doesn't play well with JOCL magic.

Это не произошло автоматически для меня; Я думаю, что он используется только при загрузке плагинов SBT. Я должен был adapt the SBT classloader:

// adapted from sbt.classpath.NativeCopyLoader 
package scalan.compilation.lms 

import java.io.File 
import java.net.{URLClassLoader, URL} 
import java.nio.file.Files 

/** 
* Loads native libraries from a temporary location in order to work around the jvm native library uniqueness restriction. 
* 
* The loader will provide native libraries listed in `explicitLibraries` and on `searchPaths` by copying them to `tempDirectory`. 
*/ 
class NativeCopyLoader(explicitLibraries: Seq[File], searchPaths: Seq[File], urls: Array[URL], parent: ClassLoader) extends URLClassLoader(urls, parent) { 
    private[this] val mapped = new collection.mutable.HashMap[String, String] 
    private[this] val tempDirectory = Files.createTempDirectory("native-library-copies").toFile 
    tempDirectory.deleteOnExit() 

    override protected def findLibrary(name: String): String = 
    synchronized { mapped.getOrElseUpdate(name, findLibrary0(name)) } 

    private[this] def findLibrary0(name: String): String = { 
    val mappedName = System.mapLibraryName(name) 
    val explicit = explicitLibraries.filter(_.getName == mappedName).toStream 
    val search = searchPaths.toStream flatMap relativeLibrary(mappedName) 
    (explicit ++ search).headOption.map(copy).orNull 
    } 
    private[this] def relativeLibrary(mappedName: String)(base: File): Seq[File] = { 
    val f = new File(base, mappedName) 
    if (f.isFile) f :: Nil else Nil 
    } 
    private[this] def copy(f: File): String = { 
    val target = new File(tempDirectory, f.getName) 
    Files.copy(f.toPath, target.toPath) 
    target.getAbsolutePath 
    } 
} 

И затем убедитесь, что он используется при загрузке классов, которые загружаются родные библиотеки. Однако это может потребовать изменения для работы с магией JOCL.