def __init__(self, convention, arg_types, return_type): """Initialize the Callback object. @param <convention>: Defines the calling convention of the function. @param <arg_types>: Defines the argument types of the function. @param <return_type>: Defines the return type of the function. """ self.callback = None # Allocate enough space for a jump, so we can hook it later. Then # convert it to a function. Of course, this isn't a function, but the # hook will override it. super(Callback, self).__init__( alloc(8, False).address, convention, arg_types, return_type) # A little hack to access the "self" argument def hook(args): """Call the callback and get the return value.""" return_value = self.callback(args) if return_value is not None: return return_value if return_type == DataType.VOID: return 0 # We will crash now :( raise ValueError('Return value is not allowed to be None.') # Hook the function and make sure the callback doesn't go out of scope self._hook = self.add_pre_hook(hook)
def __init__(self, convention, arg_types, return_type): """Initialize the Callback object. :param Convention|CallingConvention convention: Calling convention that should be used for this callback. :param iterable arg_types: Argument types of the callback. :param return_type: Return type of the callback. """ self.callback = None # Allocate enough space for a jump, so we can hook it later. Then # convert it to a function. Of course, this isn't a function, but the # hook will override it. super().__init__( alloc(8, False).address, convention, arg_types, return_type) self.add_pre_hook(self._hook)