mirror of
https://github.com/mistergibson/gxg-web-client.git
synced 2026-08-15 11:34:29 -07:00
86 lines
1.9 KiB
Ruby
86 lines
1.9 KiB
Ruby
##
|
|
# A wrapper for a calling a function in a shared library that has been
|
|
# attached via rb_define_method().
|
|
#
|
|
# The primitive slot for a NativeMethod points to the nmethod_call primitive
|
|
# which dispatches to the underlying C function.
|
|
|
|
module Rubinius
|
|
class NativeMethod < Executable
|
|
|
|
attr_reader :file
|
|
attr_reader :name
|
|
attr_reader :arity
|
|
|
|
#
|
|
# Load a dynamic library at path +library+, having name +extension_name+.
|
|
#
|
|
# +extension_name+ is used to calculate what Init_ function to call.
|
|
#
|
|
def self.load_extension(library, extension_name)
|
|
name = "Init_#{extension_name.sub(/\..*$/, '')}"
|
|
|
|
begin
|
|
lib = FFI::DynamicLibrary.new(library, FFI::DynamicLibrary::RTLD_NOW | FFI::DynamicLibrary::RTLD_GLOBAL)
|
|
rescue LoadError => e
|
|
raise LoadError::InvalidExtensionError, e.message, e
|
|
end
|
|
|
|
ver = lib.find_symbol("__X_rubinius_version")
|
|
|
|
unless ver
|
|
raise LoadError::InvalidExtensionError, "Out-of-date or not compatible. Recompile or reinstall gem (#{library})"
|
|
end
|
|
|
|
sym = lib.find_symbol(name)
|
|
|
|
unless sym
|
|
raise LoadError::InvalidExtensionError, "Missing Init_ function (#{name})"
|
|
end
|
|
|
|
entry_point = load_entry_point(library, name.to_sym, sym)
|
|
|
|
entry_point.invoke(:init, Rubinius, self, [], nil)
|
|
|
|
true
|
|
end
|
|
|
|
#
|
|
# Load extension and generate a NativeMethod for its entry point.
|
|
#
|
|
# +ptr+ is an FFI::Pointer to a C function.
|
|
#
|
|
def self.load_entry_point(library, name, ptr)
|
|
Rubinius.primitive :nativemethod_load_extension_entry_point
|
|
raise PrimitiveFailure, "Rubinius::NativeMethod3load_entry_point primitive failed: #{library}"
|
|
end
|
|
|
|
def lines
|
|
nil
|
|
end
|
|
|
|
def literals
|
|
nil
|
|
end
|
|
|
|
def line_from_ip(i)
|
|
0
|
|
end
|
|
|
|
def first_line
|
|
0
|
|
end
|
|
|
|
def defined_line
|
|
0
|
|
end
|
|
|
|
def active_path
|
|
@file
|
|
end
|
|
|
|
def scope
|
|
nil
|
|
end
|
|
end
|
|
end
|