Example #1
0
static void
gum_duk_invocation_listener_on_enter (GumInvocationListener * listener,
                                      GumInvocationContext * ic)
{
  GumDukInvocationListener * self = GUM_DUK_INVOCATION_LISTENER_CAST (listener);

  if (gum_script_backend_is_ignoring (
      gum_invocation_context_get_thread_id (ic)))
    return;

  if (self->on_enter != NULL)
  {
    GumDukInterceptor * module = self->module;
    GumDukCore * core = module->core;
    duk_context * ctx = core->ctx;
    GumDukScope scope;
    GumDukInvocationContext * jic;
    GumDukInvocationArgs * args;

    _gum_duk_scope_enter (&scope, core);

    jic = _gum_duk_interceptor_obtain_invocation_context (module);
    _gum_duk_invocation_context_reset (jic, ic);

    args = gum_duk_interceptor_obtain_invocation_args (module);
    gum_duk_invocation_args_reset (args, ic);

    duk_push_heapptr (ctx, self->on_enter);
    duk_push_heapptr (ctx, jic->object);
    duk_push_heapptr (ctx, args->object);
    _gum_duk_scope_call_method (&scope, 1);
    duk_pop (ctx);

    gum_duk_invocation_args_reset (args, NULL);
    gum_duk_interceptor_release_invocation_args (module, args);

    _gum_duk_invocation_context_reset (jic, NULL);
    if (self->on_leave != NULL)
    {
      *GUM_LINCTX_GET_FUNC_INVDATA (ic, GumDukHeapPtr) = jic;
    }
    else
    {
      _gum_duk_interceptor_release_invocation_context (module, jic);
    }

    _gum_duk_scope_leave (&scope);
  }
}
Example #2
0
static void
gum_duk_invocation_listener_on_leave (GumInvocationListener * listener,
                                      GumInvocationContext * ic)
{
  GumDukInvocationListener * self = GUM_DUK_INVOCATION_LISTENER_CAST (listener);

  if (gum_script_backend_is_ignoring (
      gum_invocation_context_get_thread_id (ic)))
    return;

  if (self->on_leave != NULL)
  {
    GumDukInterceptor * module = self->module;
    GumDukCore * core = module->core;
    duk_context * ctx = core->ctx;
    GumDukScope scope;
    GumDukInvocationContext * jic;
    GumDukInvocationReturnValue * retval;

    _gum_duk_scope_enter (&scope, core);

    jic = (self->on_enter != NULL)
        ? *GUM_LINCTX_GET_FUNC_INVDATA (ic, GumDukInvocationContext *)
        : NULL;
    if (jic == NULL)
    {
      jic = _gum_duk_interceptor_obtain_invocation_context (module);
    }
    _gum_duk_invocation_context_reset (jic, ic);

    retval = gum_duk_interceptor_obtain_invocation_return_value (module);
    gum_duk_invocation_return_value_reset (retval, ic);

    duk_push_heapptr (ctx, self->on_leave);
    duk_push_heapptr (ctx, jic->object);
    duk_push_heapptr (ctx, retval->object);
    _gum_duk_scope_call_method (&scope, 1);
    duk_pop (ctx);

    gum_duk_invocation_return_value_reset (retval, NULL);
    gum_duk_interceptor_release_invocation_return_value (module, retval);

    _gum_duk_invocation_context_reset (jic, NULL);
    _gum_duk_interceptor_release_invocation_context (module, jic);

    _gum_duk_scope_leave (&scope);
  }
Example #3
0
static gboolean
gum_emit_thread (const GumThreadDetails * details,
                 gpointer user_data)
{
  GumJscMatchContext * mc = user_data;
  GumJscCore * core = mc->self->core;
  GumJscScope scope = GUM_JSC_SCOPE_INIT (core);
  JSContextRef ctx = mc->ctx;
  JSObjectRef thread;
  JSValueRef result;
  gboolean proceed;
  gchar * str;

  if (gum_script_backend_is_ignoring (GUM_SCRIPT_BACKEND (core->backend),
      details->id))
    return TRUE;

  thread = JSObjectMake (ctx, NULL, NULL);
  _gumjs_object_set_uint (ctx, thread, "id", details->id);
  _gumjs_object_set_string (ctx, thread, "state",
      _gumjs_thread_state_to_string (details->state));
  _gumjs_object_set (ctx, thread, "context", _gumjs_cpu_context_new (ctx,
      (GumCpuContext *) &details->cpu_context, GUM_CPU_CONTEXT_READONLY, core));

  result = JSObjectCallAsFunction (ctx, mc->on_match, NULL, 1,
      (JSValueRef *) &thread, &scope.exception);
  _gum_jsc_scope_flush (&scope);

  proceed = TRUE;
  if (result != NULL && _gumjs_string_try_get (ctx, result, &str, NULL))
  {
    proceed = strcmp (str, "stop") != 0;
    g_free (str);
  }

  return proceed;
}
static gboolean
gum_emit_thread (const GumThreadDetails * details,
                 gpointer user_data)
{
  GumDukMatchContext * mc = user_data;
  GumDukScope * scope = mc->scope;
  duk_context * ctx = scope->ctx;
  gboolean proceed = TRUE;

  if (gum_script_backend_is_ignoring (details->id))
    return TRUE;

  duk_push_heapptr (ctx, mc->on_match);

  duk_push_object (ctx);
  duk_push_uint (ctx, details->id);
  duk_put_prop_string (ctx, -2, "id");
  duk_push_string (ctx, _gum_duk_thread_state_to_string (details->state));
  duk_put_prop_string (ctx, -2, "state");
  _gum_duk_push_cpu_context (ctx, (GumCpuContext *) &details->cpu_context,
      GUM_CPU_CONTEXT_READONLY, scope->core);
  duk_put_prop_string (ctx, -2, "context");

  if (_gum_duk_scope_call_sync (scope, 1))
  {
    if (duk_is_string (ctx, -1))
      proceed = strcmp (duk_require_string (ctx, -1), "stop") != 0;
  }
  else
  {
    proceed = FALSE;
  }
  duk_pop (ctx);

  return proceed;
}