mirror of
				https://github.com/c64scene-ar/llvm-6502.git
				synced 2025-11-04 05:17:07 +00:00 
			
		
		
		
	Before this fix, the LLVM Python bindings on SVN trunk always fail with: Exception: LLVM shared library not found! since it's still looking for a library named "LLVM-3.1svn". Besides updating the LLVM version in the library name, this patch also changes llvm.get_library() to make it possible to run the unit tests without installing the LLVM shared library into a default linker search path. e.g. after this patch, running the llvm/python unit tests with: LD_LIBRARY_PATH=../build/Debug+Asserts/lib nosetests -v bindings/python/llvm/tests/ would work on Linux. Patch from Scott Tsai (with some minor modifications) Patch also acked by Gregory Szorc git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@168390 91177308-0d34-0410-b5e6-96231b3b80d8
		
			
				
	
	
		
			127 lines
		
	
	
		
			3.8 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
			
		
		
	
	
			127 lines
		
	
	
		
			3.8 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
#===- common.py - Python LLVM Bindings -----------------------*- python -*--===#
 | 
						|
#
 | 
						|
#                     The LLVM Compiler Infrastructure
 | 
						|
#
 | 
						|
# This file is distributed under the University of Illinois Open Source
 | 
						|
# License. See LICENSE.TXT for details.
 | 
						|
#
 | 
						|
#===------------------------------------------------------------------------===#
 | 
						|
 | 
						|
from ctypes import POINTER
 | 
						|
from ctypes import c_void_p
 | 
						|
from ctypes import cdll
 | 
						|
 | 
						|
import ctypes.util
 | 
						|
import platform
 | 
						|
 | 
						|
# LLVM_VERSION: sync with PACKAGE_VERSION in autoconf/configure.ac and CMakeLists.txt
 | 
						|
#               but leave out the 'svn' suffix.
 | 
						|
LLVM_VERSION = '3.3'
 | 
						|
 | 
						|
__all__ = [
 | 
						|
    'c_object_p',
 | 
						|
    'get_library',
 | 
						|
]
 | 
						|
 | 
						|
c_object_p = POINTER(c_void_p)
 | 
						|
 | 
						|
class LLVMObject(object):
 | 
						|
    """Base class for objects that are backed by an LLVM data structure.
 | 
						|
 | 
						|
    This class should never be instantiated outside of this package.
 | 
						|
    """
 | 
						|
    def __init__(self, ptr, ownable=True, disposer=None):
 | 
						|
        assert isinstance(ptr, c_object_p)
 | 
						|
 | 
						|
        self._ptr = self._as_parameter_ = ptr
 | 
						|
 | 
						|
        self._self_owned = True
 | 
						|
        self._ownable = ownable
 | 
						|
        self._disposer = disposer
 | 
						|
 | 
						|
        self._owned_objects = []
 | 
						|
 | 
						|
    def take_ownership(self, obj):
 | 
						|
        """Take ownership of another object.
 | 
						|
 | 
						|
        When you take ownership of another object, you are responsible for
 | 
						|
        destroying that object. In addition, a reference to that object is
 | 
						|
        placed inside this object so the Python garbage collector will not
 | 
						|
        collect the object while it is still alive in libLLVM.
 | 
						|
 | 
						|
        This method should likely only be called from within modules inside
 | 
						|
        this package.
 | 
						|
        """
 | 
						|
        assert isinstance(obj, LLVMObject)
 | 
						|
 | 
						|
        self._owned_objects.append(obj)
 | 
						|
        obj._self_owned = False
 | 
						|
 | 
						|
    def from_param(self):
 | 
						|
        """ctypes function that converts this object to a function parameter."""
 | 
						|
        return self._as_parameter_
 | 
						|
 | 
						|
    def __del__(self):
 | 
						|
        if not hasattr(self, '_self_owned') or not hasattr(self, '_disposer'):
 | 
						|
            return
 | 
						|
 | 
						|
        if self._self_owned and self._disposer:
 | 
						|
            self._disposer(self)
 | 
						|
 | 
						|
class CachedProperty(object):
 | 
						|
    """Decorator that caches the result of a property lookup.
 | 
						|
 | 
						|
    This is a useful replacement for @property. It is recommended to use this
 | 
						|
    decorator on properties that invoke C API calls for which the result of the
 | 
						|
    call will be idempotent.
 | 
						|
    """
 | 
						|
    def __init__(self, wrapped):
 | 
						|
        self.wrapped = wrapped
 | 
						|
        try:
 | 
						|
            self.__doc__ = wrapped.__doc__
 | 
						|
        except: # pragma: no cover
 | 
						|
            pass
 | 
						|
 | 
						|
    def __get__(self, instance, instance_type=None):
 | 
						|
        if instance is None:
 | 
						|
            return self
 | 
						|
 | 
						|
        value = self.wrapped(instance)
 | 
						|
        setattr(instance, self.wrapped.__name__, value)
 | 
						|
 | 
						|
        return value
 | 
						|
 | 
						|
def get_library():
 | 
						|
    """Obtain a reference to the llvm library."""
 | 
						|
 | 
						|
    # On Linux, ctypes.cdll.LoadLibrary() respects LD_LIBRARY_PATH
 | 
						|
    # while ctypes.util.find_library() doesn't.
 | 
						|
    # See http://docs.python.org/2/library/ctypes.html#finding-shared-libraries
 | 
						|
    #
 | 
						|
    # To make it possible to run the unit tests without installing the LLVM shared
 | 
						|
    # library into a default linker search path.  Always Try ctypes.cdll.LoadLibrary()
 | 
						|
    # with all possible library names first, then try ctypes.util.find_library().
 | 
						|
 | 
						|
    names = ['LLVM-' + LLVM_VERSION, 'LLVM-' + LLVM_VERSION + 'svn']
 | 
						|
    t = platform.system()
 | 
						|
    if t == 'Darwin':
 | 
						|
        pfx, ext = 'lib', '.dylib'
 | 
						|
    elif t == 'Windows':
 | 
						|
        pfx, ext = '', '.dll'
 | 
						|
    else:
 | 
						|
        pfx, ext = 'lib', '.so'
 | 
						|
 | 
						|
    for i in names:
 | 
						|
        try:
 | 
						|
            lib = cdll.LoadLibrary(pfx + i + ext)
 | 
						|
        except OSError:
 | 
						|
            pass
 | 
						|
        else:
 | 
						|
            return lib
 | 
						|
 | 
						|
    for i in names:
 | 
						|
        t = ctypes.util.find_library(i)
 | 
						|
        if t:
 | 
						|
            return cdll.LoadLibrary(t)
 | 
						|
    raise Exception('LLVM shared library not found!')
 |