9

When running a new project utilising LeadIQ's play boilerplate, we will run into an UnsatisfiedLinkError in older versions of JNA below version 5.7.0.

I think this is due to incompatible binaries between the ARM M1 architecture. How can it be resolved?

Here's the full stack trace, showing "no matching architecture" from the JNA binaries.

[error] java.lang.UnsatisfiedLinkError: /Users/zackng/Library/Caches/JNA/temp/jna1415930593236960966.tmp: dlopen(/Users/zackng/Library/Caches/JNA/temp/jna1415930593236960966.tmp, 1): no suitable image found.  Did find:
[error]     /Users/zackng/Library/Caches/JNA/temp/jna1415930593236960966.tmp: no matching architecture in universal wrapper
[error]     /Users/zackng/Library/Caches/JNA/temp/jna1415930593236960966.tmp: no matching architecture in universal wrapper
[error]     at java.base/java.lang.ClassLoader$NativeLibrary.load0(Native Method)
[error]     at java.base/java.lang.ClassLoader$NativeLibrary.load(ClassLoader.java:2442)
[error]     at java.base/java.lang.ClassLoader$NativeLibrary.loadLibrary(ClassLoader.java:2498)
[error]     at java.base/java.lang.ClassLoader.loadLibrary0(ClassLoader.java:2694)
[error]     at java.base/java.lang.ClassLoader.loadLibrary(ClassLoader.java:2627)
[error]     at java.base/java.lang.Runtime.load0(Runtime.java:768)
[error]     at java.base/java.lang.System.load(System.java:1837)
[error]     at com.sun.jna.Native.loadNativeDispatchLibraryFromClasspath(Native.java:1018)
[error]     at com.sun.jna.Native.loadNativeDispatchLibrary(Native.java:988)
[error]     at com.sun.jna.Native.<clinit>(Native.java:195)
[error]     at io.methvin.watchservice.jna.CarbonAPI.<clinit>(CarbonAPI.java:20)
[error]     at io.methvin.watchservice.jna.CFStringRef.toCFString(CFStringRef.java:23)
[error]     at io.methvin.watchservice.MacOSXListeningWatchService.register(MacOSXListeningWatchService.java:127)
[error]     at io.methvin.watchservice.WatchablePath.register(WatchablePath.java:50)
[error]     at io.methvin.watcher.DirectoryWatcher.register(DirectoryWatcher.java:400)
[error]     at io.methvin.watcher.DirectoryWatcher.registerAll(DirectoryWatcher.java:373)
[error]     at io.methvin.watcher.DirectoryWatcher.<init>(DirectoryWatcher.java:193)
[error]     at io.methvin.watcher.DirectoryWatcher$Builder.build(DirectoryWatcher.java:122)
[error]     at play.dev.filewatch.DefaultFileWatchService.watch(DefaultFileWatchService.scala:44)
[error]     at play.dev.filewatch.FileWatchService$$anon$1.watch(FileWatchService.scala:95)
[error]     at play.runsupport.Reloader.<init>(Reloader.scala:443)
[error]     at play.runsupport.Reloader$.reloader$lzycompute$1(Reloader.scala:283)
[error]     at play.runsupport.Reloader$.play$runsupport$Reloader$$reloader$1(Reloader.scala:275)
[error]     at play.runsupport.Reloader$.startDevMode(Reloader.scala:306)
[error]     at play.sbt.run.PlayRun$.devModeServer$lzycompute$1(PlayRun.scala:100)
[error]     at play.sbt.run.PlayRun$.devModeServer$1(PlayRun.scala:83)
[error]     at play.sbt.run.PlayRun$.$anonfun$playRunTask$3(PlayRun.scala:107)
[error]     at play.sbt.run.PlayRun$.$anonfun$playRunTask$3$adapted(PlayRun.scala:67)
[error]     at scala.Function1.$anonfun$compose$1(Function1.scala:49)
[error] stack trace is suppressed; run last Compile / run for the full output
[error] (Compile / run) java.lang.UnsatisfiedLinkError: /Users/zackng/Library/Caches/JNA/temp/jna1415930593236960966.tmp: dlopen(/Users/zackng/Library/Caches/JNA/temp/jna1415930593236960966.tmp, 1): no suitable image found.  Did find:
[error]     /Users/zackng/Library/Caches/JNA/temp/jna1415930593236960966.tmp: no matching architecture in universal wrapper
[error]     /Users/zackng/Library/Caches/JNA/temp/jna1415930593236960966.tmp: no matching architecture in universal wrapper
[error] Total time: 1 s, completed Dec 15, 2021, 10:36:16 AM
Daniel Widdis
  • 8,424
  • 13
  • 41
  • 63
Zack
  • 189
  • 1
  • 6

2 Answers2

12

There are two compatibility issues associated with macOS and M1 chips that can cause UnsatisfiedLinkErrors.

The issue you experienced was associated with a lack of support for aarch64, the M1 architecture. This was fixed in JNA 5.7.0, and upgrading to that or later versions resolves the problem.

Another issue that may produce this error is associated with how Apple changed the way system libraries are loaded in macOS 11 (Big Sur), continuing on in future versions.

From the macOS Big Sur 11.0.1 Release Notes:

New in macOS Big Sur 11.0.1, the system ships with a built-in dynamic linker cache of all system-provided libraries. As part of this change, copies of dynamic libraries are no longer present on the filesystem. Code that attempts to check for dynamic library presence by looking for a file at a path or enumerating a directory will fail. Instead, check for library presence by attempting to dlopen() the path, which will correctly check for the library in the cache.

JNA fixed this loading issue in Release 5.6.0.

Daniel Widdis
  • 8,424
  • 13
  • 41
  • 63
  • 1
    Nice, very nice, this led me in the right direction. Had an Elasticsearch dependency pointing at 5.5.0, sitting on an M1 Mac. Just upped it to 5.7.0 and voila. – Wrench Apr 04 '22 at 13:20
  • 1
    @Wrench why not 5.11.0? :) – Daniel Widdis Apr 04 '22 at 14:25
  • Was part of a spring-data-elasticsearch:4.2.10 dependency (JNA 5.5.0 that is), just wanted to bump it to something that works for now, as we are replacing ElasticSearch with OpenSearch next week, it will all go away. :) – Wrench Apr 04 '22 at 19:00
  • 3
    I'm on Mac Monterey 12.5.1. Using JNA 5.8.0. But still having the same issue. Any help appreciated. Do I need any changes to mac settings ? – Harshit Bansal Aug 24 '22 at 12:15
  • 1
    Nothing to do with your Mac. There is an old version from some project somewhere in your dependencies or parent POM. – Daniel Widdis Aug 24 '22 at 13:27
9

Quoted from GitHub

And replacing .sbt/boot/scala-2.12.14/org.scala-sbt/sbt/1.5.5/jna- 5.5.0.jar with a jna-5.8.0.jar fixes the issue, so bumping the dependency in sbt.io is definitely required

Basically remove the existing jna in ../sbt/1.5.5/jna-... and copy new jar of jna version >= 5.6.0 in as jna-v.v.v.jar

Specifically, I'm using 5.10.0 and the server runs now! :tada:

Credits to Github user vbabenkoru and Elia for helping me with this!

EDIT: Amended to 5.6.0 as per the release notes, thanks Daniel Widdis for pointing it out!

Zack
  • 189
  • 1
  • 6