示例#1
0
void
cleanup_task(cleanup_args *args) {
    spawn_args *a = args->spargs;
    bool threw_exception = args->threw_exception;
    rust_task *task = a->task;

    {
        scoped_lock with(task->kill_lock);
        if (task->killed && !threw_exception) {
            LOG(task, task, "Task killed during termination");
            threw_exception = true;
        }
    }

    // Clean up TLS. This will only be set if TLS was used to begin with.
    // Because this is a crust function, it must be called from the C stack.
    if (task->task_local_data_cleanup != NULL) {
        // This assert should hold but it's not our job to ensure it (and
        // the condition might change). Handled in libcore/task.rs.
        // assert(task->task_local_data != NULL);
        task->task_local_data_cleanup(task->task_local_data);
        task->task_local_data = NULL;
    }

    // FIXME (#2676): For performance we should do the annihilator
    // instead of the cycle collector even under normal termination, but
    // since that would hide memory management errors (like not derefing
    // boxes), it needs to be disableable in debug builds.
    if (threw_exception) {
        // FIXME (#2676): When the annihilator is more powerful and
        // successfully runs resource destructors, etc. we can get rid
        // of this cc
        cc::do_cc(task);
        annihilate_boxes(task);
    }
    cc::do_final_cc(task);

    task->die();

    task->notify(!threw_exception);

    if (threw_exception) {
#ifndef __WIN32__
        task->conclude_failure();
#else
        assert(false && "Shouldn't happen");
#endif
    }
}
示例#2
0
void
cleanup_task(cleanup_args *args) {
    spawn_args *a = args->spargs;
    bool threw_exception = args->threw_exception;
    rust_task *task = a->task;

    {
        scoped_lock with(task->kill_lock);
        if (task->killed && !threw_exception) {
            LOG(task, task, "Task killed during termination");
            threw_exception = true;
        }
    }

    // FIXME: For performance we should do the annihilator instead
    // of the cycle collector even under normal termination, but
    // since that would hide memory management errors (like not derefing
    // boxes), it needs to be disableable in debug builds.
    if (threw_exception) {
        // FIXME: When the annihilator is more powerful and successfully
        // runs resource destructors, etc. we can get rid of this cc
        cc::do_cc(task);
        annihilate_boxes(task);
    }
    cc::do_final_cc(task);

    task->die();

    task->notify(!threw_exception);

    if (threw_exception) {
#ifndef __WIN32__
        task->conclude_failure();
#else
        assert(false && "Shouldn't happen");
#endif
    }
}