void JitInstanceMemberFunction::compileVTableIndirectionFunction() { m_jit_virtual_indirection_function = jit_function_create((jit_context_t)m_jit_context.context, toJitSignature(m_eAbi, getSignature())); o_assert(m_jit_virtual_indirection_function.function); jit_context_build_start((jit_context_t)m_jit_context.context); size_t argCount = getSignature()->getParameterCount()+1; // parameters+this jit_value_t* args = o_allocate_n(argCount, jit_value_t); // The indirection has the same signature as the indirected one jit_value_t this_pointer = jit_value_get_param((jit_function_t)m_jit_virtual_indirection_function.function, 0); jit_value_t vtable_index = jit_value_create_nint_constant((jit_function_t)m_jit_virtual_indirection_function.function, jit_type_nuint, getInstanceMemberFunction()->getVirtualTableIndex()); jit_value_t vtable_array = jit_insn_load_relative ((jit_function_t)m_jit_virtual_indirection_function.function, this_pointer, 0, jit_type_void_ptr); jit_value_t vtable_pointer = jit_insn_load_elem((jit_function_t)m_jit_virtual_indirection_function.function, vtable_array, vtable_index, jit_type_void_ptr); size_t i = 0; for(;i<argCount;++i) { args[i] = jit_value_get_param((jit_function_t)m_jit_virtual_indirection_function.function, i); } jit_insn_call_indirect_vtable ((jit_function_t)m_jit_virtual_indirection_function.function, vtable_pointer, jit_function_get_signature((jit_function_t)m_jit_function.function), args, argCount, 0); int result = jit_function_compile((jit_function_t)m_jit_virtual_indirection_function.function); o_assert(result != 0); jit_context_build_end((jit_context_t)m_jit_context.context); o_deallocate_n(args, argCount, jit_value_t); }
jit_value jit_function::insn_call_indirect_vtable (const jit_value& value, jit_type_t signature, jit_value_t *args, unsigned int num_args, int flags) { value_wrap(jit_insn_call_indirect_vtable (func, value.raw(), signature, args, num_args, flags)); }