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

OSError importing wand.image on Termux (missing glibc) #409

Closed
bmintz opened this issue Apr 25, 2019 · 3 comments

Comments

Projects
None yet
2 participants
@bmintz
Copy link

commented Apr 25, 2019

On Termux, I get the following traceback:

>>> import wand.image
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File ".venv/lib/python3.7/site-packages/wand/image.py", line 19, in <module>
    from .api import libc, libmagick, library
  File ".venv/lib/python3.7/site-packages/wand/api.py", line 221, in <module>
    libc = ctypes.cdll.LoadLibrary('libc.so.6')
  File "/data/data/com.termux/files/usr/lib/python3.7/ctypes/__init__.py", line 434, in LoadLibrary
    return self._dlltype(name)
  File "/data/data/com.termux/files/usr/lib/python3.7/ctypes/__init__.py", line 356, in __init__
    self._handle = _dlopen(self._name, mode)
OSError: dlopen failed: library "libc.so.6" not found

This makes sense as Termux does not provide glibc.

Wand version: 0.5.2
Python version: 3.7.3

The offending code appears to be here:

wand/wand/api.py

Lines 218 to 221 in 6f305a9

elif sys.platform.startswith(('dragonfly', 'freebsd')):
libc = ctypes.cdll.LoadLibrary(ctypes.util.find_library('c'))
else:
libc = ctypes.cdll.LoadLibrary('libc.so.6')

Indeed, changing sys.platform to 'freebsd' and then running the import, does work. Is there any reason that the generic libc is only used on FreeBSD and DragonFly BSD? Perhaps ctypes.util.find_library('c') could be used every time? Or, maybe ImportError could be raised when an OSError is encountered here?

@emcconville

This comment has been minimized.

Copy link
Owner

commented Apr 25, 2019

We just need another elif for platforms using bionic, or create another loop...try...return method like wand.api.load_library().

Sadly, I do not have the time / resources to develop against that platform. But the second options can be something like...

diff --git a/wand/api.py b/wand/api.py
index 38e19bd..f955853 100644
--- a/wand/api.py
+++ b/wand/api.py
@@ -218,7 +218,14 @@ else:
     elif sys.platform.startswith(('dragonfly', 'freebsd')):
         libc = ctypes.cdll.LoadLibrary(ctypes.util.find_library('c'))
     else:
-        libc = ctypes.cdll.LoadLibrary('libc.so.6')
+        libc_paths = ('libc.so.6', 'libc.so', 'libc.a',
+                      ctypes.util.find_library('c'))
+        for libc_path in libc_paths:
+            try:
+                libc = ctypes.cdll.LoadLibrary(libc_path)
+                break
+            except (IOError, OSError):
+                continue
     libc.fdopen.argtypes = [ctypes.c_int, ctypes.c_char_p]
     libc.fdopen.restype = ctypes.c_void_p
     libc.fflush.argtypes = [ctypes.c_void_p]

Let me know if the above suggested patch works, or if you know a way to identify bionic platform via standard Python modules.

@bmintz

This comment has been minimized.

Copy link
Author

commented Apr 25, 2019

That patch works for me.

#365 appears to also fix this issue, and seems to be cleaner and without an explicit test for BSD. Thoughts on using that approach?

@emcconville emcconville added this to the Wand 0.5.4 milestone Apr 25, 2019

@emcconville

This comment has been minimized.

Copy link
Owner

commented Apr 25, 2019

That patch works for me.

Cool.

Thoughts on using that approach?

I think that approach punts the problem down field, but suggests a few good points. I'll spend some time reworking the solution. Honestly, we only use libc for fopen & fflush, and already have a fallback in place -- if libc is not available. Might be worth reducing complexity.

emcconville added a commit that referenced this issue Apr 26, 2019

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.