Exemple #1
0
static gboolean
mono_thread_info_core_resume (MonoThreadInfo *info)
{
	gboolean res = FALSE;
	if (info->create_suspended) {
		MonoNativeThreadId tid = mono_thread_info_get_tid (info);
		/* Have to special case this, as the normal suspend/resume pair are racy, they don't work if he resume is received before the suspend */
		info->create_suspended = FALSE;
		mono_threads_core_resume_created (info, tid);
		return TRUE;
	}

	switch (mono_threads_transition_request_resume (info)) {
	case ResumeError:
		res = FALSE;
		break;
	case ResumeOk:
		res = TRUE;
		break;
	case ResumeInitSelfResume:
		resume_self_suspended (info);
		res = TRUE;
		break;
	case ResumeInitAsyncResume:
		resume_async_suspended (info);
		res = TRUE;
		break;
	case ResumeInitBlockingResume:
		resume_blocking_suspended (info);
		res = TRUE;
		break;
	}

	return res;
}
Exemple #2
0
static gboolean
mono_thread_info_core_resume (MonoThreadInfo *info)
{
	gboolean result;
	MonoNativeThreadId tid = mono_thread_info_get_tid (info);
	if (info->create_suspended) {
		/* Have to special case this, as the normal suspend/resume pair are racy, they don't work if he resume is received before the suspend */
		info->create_suspended = FALSE;
		mono_threads_core_resume_created (info, tid);
		return TRUE;
	}

	MONO_SEM_WAIT_UNITERRUPTIBLE (&info->suspend_semaphore);

	THREADS_DEBUG ("resume %x IN COUNT %d\n", tid, info->suspend_count);

	if (info->suspend_count <= 0) {
		MONO_SEM_POST (&info->suspend_semaphore);
		return FALSE;
	}

	/*
	 * The theory here is that if we manage to suspend the thread it means it did not
	 * start cleanup since it take the same lock. 
	*/
	g_assert (mono_thread_info_get_tid (info));

	if (--info->suspend_count == 0) {
		if (mono_thread_info_suspend_state (info) == STATE_SELF_SUSPENDED) {
			MONO_SEM_POST (&info->resume_semaphore);
			MONO_SEM_WAIT_UNITERRUPTIBLE (&info->finish_resume_semaphore);
			result = TRUE;
		} else {
			result = mono_threads_core_resume (info);
		}
		info->thread_state &= ~SUSPEND_STATE_MASK;
	} else {
		result = TRUE;
	}

	MONO_SEM_POST (&info->suspend_semaphore);
	return result;
}
Exemple #3
0
gboolean
mono_thread_info_resume (MonoNativeThreadId tid)
{
	gboolean result = TRUE;
	MonoThreadHazardPointers *hp = mono_hazard_pointer_get ();	
	MonoThreadInfo *info = mono_thread_info_lookup (tid); /*info on HP1*/

	if (!info)
		return FALSE;

	if (info->create_suspended) {
		/* Have to special case this, as the normal suspend/resume pair are racy, they don't work if he resume is received before the suspend */
		info->create_suspended = FALSE;
		mono_threads_core_resume_created (info, tid);
		return TRUE;
	}

	MONO_SEM_WAIT_UNITERRUPTIBLE (&info->suspend_semaphore);

	THREADS_DEBUG ("resume %x IN COUNT %d\n",tid, info->suspend_count);

	if (info->suspend_count <= 0) {
		MONO_SEM_POST (&info->suspend_semaphore);
		mono_hazard_pointer_clear (hp, 1);
		return FALSE;
	}

	/*
	 * The theory here is that if we manage to suspend the thread it means it did not
	 * start cleanup since it take the same lock. 
	*/
	g_assert (mono_thread_info_get_tid (info));

	if (--info->suspend_count == 0)
		result = mono_thread_info_resume_internal (info);

	MONO_SEM_POST (&info->suspend_semaphore);
	mono_hazard_pointer_clear (hp, 1);
	mono_atomic_store_release (&mono_thread_info_current ()->inside_critical_region, FALSE);

	return result;
}