⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 p_c_dll.c

📁 操作系统课程设计
💻 C
字号:
#include "P_C_Dll.h"
#include "loop_queue.h"
#include "stack.h"

#include <stdio.h>
#include <stdlib.h>
#include <windows.h>

#define WM_SETTIMER WM_USER + 100

/* some global variable(s) */
HANDLE g_hProducerThread = NULL;
DWORD g_dwProducerThreadId;

HANDLE g_hConsumerThread = NULL;
DWORD g_dwConsumerThreadId;

HANDLE g_hMutex = NULL;
HANDLE g_hFullSemaphore = NULL;
HANDLE g_hEmptySemaphore = NULL;

PLOOP_QUEUE g_LQueue = NULL;
PSTACK g_Stack = NULL;

UINT g_uProducerTimer = 1000;
UINT g_uConsumerTimer = 1000;

ContainerType g_C = C_LOOP_QUEUE;

void PrintLocalTime();
void Producer();
void Consumer();

DWORD WINAPI ProducerFunc(LPVOID);
DWORD WINAPI ConsumerFunc(LPVOID);

void Initialize(ContainerType c, UINT producerTimer, UINT consumerTimer)
{
	g_C = c;
	g_uProducerTimer = producerTimer;
	g_uConsumerTimer = consumerTimer;

	if(g_C == C_LOOP_QUEUE)
		g_LQueue = CreateLQueue();
	else
		g_Stack = CreateStack();

	g_hMutex = CreateMutex(NULL, FALSE, NULL);
	g_hFullSemaphore = CreateSemaphore(NULL, 0, MAX_SEM_SIZE, NULL);
	g_hEmptySemaphore = CreateSemaphore(NULL, MAX_SEM_SIZE, MAX_SEM_SIZE, NULL);

	/* srand(GetTickCount()); */

}

void ProducerStart()
{
	g_hProducerThread = CreateThread(NULL, 0, ProducerFunc, NULL, CREATE_SUSPENDED, &g_dwProducerThreadId);
}

void ConsumerStart()
{
	g_hConsumerThread = CreateThread(NULL, 0, ConsumerFunc, NULL, CREATE_SUSPENDED, &g_dwConsumerThreadId);
}

/* modify the timer of the producer */
void SetProducerTimer(UINT producerTimer)
{
	g_uProducerTimer = producerTimer;
	PostThreadMessage(g_dwProducerThreadId, WM_SETTIMER, 0, 0);
}

void SetConsumerTimer(UINT consumerTimer)
{
	g_uConsumerTimer = consumerTimer;
	PostThreadMessage(g_dwConsumerThreadId, WM_SETTIMER, 0, 0);
}

/* suspend the both producer thread and consumer thread */
void SuspendAll()
{
	SuspendThread(g_hProducerThread);
	SuspendThread(g_hConsumerThread);
}

void ResumeAll()
{
	ResumeThread(g_hProducerThread);
	ResumeThread(g_hConsumerThread);
}

void StopAll()
{
	PostThreadMessage(g_dwConsumerThreadId, WM_QUIT, 0, 0);
	PostThreadMessage(g_dwConsumerThreadId, WM_QUIT, 0, 0);
}

/* 生产者线程函数 */
DWORD WINAPI ProducerFunc(LPVOID lpParameter)
{
	MSG msg;
	UINT producerTimerId;

	/* Create a message queue for this thread */
	PeekMessage(&msg, NULL, 0, 0, PM_NOREMOVE);
	producerTimerId = SetTimer(NULL, 0, g_uProducerTimer, NULL);

	while(GetMessage(&msg, NULL, 0, 0))
	{
		if(msg.message == WM_TIMER)
		{
			WaitForSingleObject(g_hEmptySemaphore, INFINITE);
			WaitForSingleObject(g_hMutex, INFINITE);

			Producer();

			ReleaseMutex(g_hMutex);
			ReleaseSemaphore(g_hFullSemaphore, 1, NULL);
		}
		else if(msg.message == WM_SETTIMER)
		{
			KillTimer(NULL, producerTimerId);
			producerTimerId = SetTimer(NULL, 0, g_uProducerTimer, NULL);
		}
		else
		{
			TranslateMessage(&msg);
			DispatchMessage(&msg);
		}
	}

	KillTimer(NULL, producerTimerId);
	return 0;
}

/* 消费者线程函数 */
DWORD WINAPI ConsumerFunc(LPVOID lpParameter)
{
	MSG msg;
	UINT consumerTimerId;

	PeekMessage(&msg, NULL, 0, 0, PM_NOREMOVE);
	consumerTimerId = SetTimer(NULL, 0, g_uConsumerTimer, NULL);

	while(GetMessage(&msg, NULL, 0, 0))
	{
		if(msg.message == WM_TIMER)
		{
			WaitForSingleObject(g_hFullSemaphore, INFINITE);
			WaitForSingleObject(g_hMutex, INFINITE);

			Consumer();

			ReleaseMutex(g_hMutex);
			ReleaseSemaphore(g_hEmptySemaphore, 1, NULL);
		}
		else if(msg.message == WM_SETTIMER)
		{
			KillTimer(NULL, consumerTimerId);
			consumerTimerId = SetTimer(NULL, 0, g_uConsumerTimer, NULL);
		}
		else
		{
			TranslateMessage(&msg);
			DispatchMessage(&msg);
		}
	}

	KillTimer(NULL, consumerTimerId);
	return 0;
}

/* 生产一个数据 */
void Producer()
{
	ElemType e;
	BOOL res = FALSE;

	srand(GetTickCount());
	e = abs(rand()) % MAX_SEM_SIZE;

	if(g_C == C_LOOP_QUEUE)
		res = EnLQueue(g_LQueue, e);
	else
		res = PushStack(g_Stack, e);

	if(res)
	{
		printf("Producer: ");
		PrintLocalTime();
		printf(" product %d\n", e);
	}
}

/* 消费一个数据 */
void Consumer()
{
	ElemType e;
	BOOL res = FALSE;

	if(g_C == C_LOOP_QUEUE)
		res = DeLQueue(g_LQueue, &e);
	else
		res = PopStack(g_Stack, &e);

	if(res)
	{
		printf("                                     ");
		printf("Consumer: ");
		PrintLocalTime();
		printf(" consume %d\n", e);
	}
}

void PrintLocalTime()
{
	SYSTEMTIME sysTime;
	GetLocalTime(&sysTime);

	if(sysTime.wHour < 10)
		printf("0");
	printf("%d:", sysTime.wHour);

	if(sysTime.wMinute < 10)
		printf("0");
	printf("%d:", sysTime.wMinute);

	if(sysTime.wSecond < 10)
		printf("0");
	printf("%d.", sysTime.wSecond);

	printf("%d", sysTime.wMilliseconds);
}

BOOL WINAPI DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID lpvReserved)
{
	switch(dwReason)
	{
	case DLL_PROCESS_ATTACH:
		g_uProducerTimer = 1000;
		g_uConsumerTimer = 1000;
		g_C = C_LOOP_QUEUE;
		break;
	case DLL_PROCESS_DETACH:
		if(NULL != g_hProducerThread)
			CloseHandle(g_hProducerThread);
		if(NULL != g_hConsumerThread)
			CloseHandle(g_hConsumerThread);
		if(NULL != g_LQueue)
			DestroyLQueue(&g_LQueue);
		if(NULL != g_Stack)
			DestroyStack(&g_Stack);
		break;
	}

	return TRUE;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -