Example #1
0
bool
MachTask::StartExceptionThread(DNBError &err)
{
    DNBLogThreadedIf(LOG_EXCEPTIONS, "MachTask::%s ( )", __FUNCTION__);
    task_t task = TaskPortForProcessID(err);
    if (MachTask::IsValid(task))
    {
        // Got the mach port for the current process
        mach_port_t task_self = mach_task_self ();

        // Allocate an exception port that we will use to track our child process
        err = ::mach_port_allocate (task_self, MACH_PORT_RIGHT_RECEIVE, &m_exception_port);
        if (err.Fail())
            return false;

        // Add the ability to send messages on the new exception port
        err = ::mach_port_insert_right (task_self, m_exception_port, m_exception_port, MACH_MSG_TYPE_MAKE_SEND);
        if (err.Fail())
            return false;

        // Save the original state of the exception ports for our child process
        SaveExceptionPortInfo();

        // We weren't able to save the info for our exception ports, we must stop...
        if (m_exc_port_info.mask == 0)
        {
            err.SetErrorString("failed to get exception port info");
            return false;
        }

        // Set the ability to get all exceptions on this port
        err = ::task_set_exception_ports (task, m_exc_port_info.mask, m_exception_port, EXCEPTION_DEFAULT | MACH_EXCEPTION_CODES, THREAD_STATE_NONE);
        if (DNBLogCheckLogBit(LOG_EXCEPTIONS) || err.Fail())
        {
            err.LogThreaded("::task_set_exception_ports ( task = 0x%4.4x, exception_mask = 0x%8.8x, new_port = 0x%4.4x, behavior = 0x%8.8x, new_flavor = 0x%8.8x )",
                            task,
                            m_exc_port_info.mask,
                            m_exception_port,
                            (EXCEPTION_DEFAULT | MACH_EXCEPTION_CODES),
                            THREAD_STATE_NONE);
        }

        if (err.Fail())
            return false;

        // Create the exception thread
        err = ::pthread_create (&m_exception_thread, NULL, MachTask::ExceptionThread, this);
        return err.Success();
    }
    else
    {
        DNBLogError("MachTask::%s (): task invalid, exception thread start failed.", __FUNCTION__);
    }
    return false;
}
Example #2
0
nub_addr_t
MachTask::GetDYLDAllImageInfosAddress (DNBError& err)
{
    struct hack_task_dyld_info dyld_info;
    mach_msg_type_number_t count = TASK_DYLD_INFO_COUNT;
    // Make sure that COUNT isn't bigger than our hacked up struct hack_task_dyld_info.
    // If it is, then make COUNT smaller to match.
    if (count > (sizeof(struct hack_task_dyld_info) / sizeof(natural_t)))
        count = (sizeof(struct hack_task_dyld_info) / sizeof(natural_t));

    task_t task = TaskPortForProcessID (err);
    if (err.Success())
    {
        err = ::task_info (task, TASK_DYLD_INFO, (task_info_t)&dyld_info, &count);
        if (err.Success())
        {
            // We now have the address of the all image infos structure
            return dyld_info.all_image_info_addr;
        }
    }
    return INVALID_NUB_ADDRESS;
}
Example #3
0
bool
MachTask::StartExceptionThread(DNBError &err)
{
    DNBLogThreadedIf(LOG_EXCEPTIONS, "MachTask::%s ( )", __FUNCTION__);
    task_t task = TaskPortForProcessID(err);
    if (MachTask::IsValid(task))
    {
        // Got the mach port for the current process
        mach_port_t task_self = mach_task_self ();

        // Allocate an exception port that we will use to track our child process
        err = ::mach_port_allocate (task_self, MACH_PORT_RIGHT_RECEIVE, &m_exception_port);
        if (err.Fail())
            return false;

        // Add the ability to send messages on the new exception port
        err = ::mach_port_insert_right (task_self, m_exception_port, m_exception_port, MACH_MSG_TYPE_MAKE_SEND);
        if (err.Fail())
            return false;

        // Save the original state of the exception ports for our child process
        SaveExceptionPortInfo();

        // Set the ability to get all exceptions on this port
        err = ::task_set_exception_ports (task, EXC_MASK_ALL, m_exception_port, EXCEPTION_DEFAULT | MACH_EXCEPTION_CODES, THREAD_STATE_NONE);
        if (err.Fail())
            return false;

        // Create the exception thread
        err = ::pthread_create (&m_exception_thread, NULL, MachTask::ExceptionThread, this);
        return err.Success();
    }
    else
    {
        DNBLogError("MachTask::%s (): task invalid, exception thread start failed.", __FUNCTION__);
    }
    return false;
}