📄 program11.c
字号:
#include "libepc.h"
#include "os_cpu.h"
#include "os_cfg.h"
#include "ucos_ii.h"
#include <stdlib.h>
#define STACK_SIZE 1000
#define THREADS 2 /* No more than 6 */
#define RESOURCES 2 /* No more than 8 */
typedef enum
{
DORMANT = 0,
PENDING = 1,
READY = 2,
RUNNING = 3,
SLEEPING= 4
} THREAD_STATE ;
extern void AcquireResources(int, int) ;
extern void ReleaseResources(int, int) ;
BOOL Acquire1Resource(int, int) ;
void Release1Resource(int, int) ;
PRIVATE void Analyze(void) ;
PRIVATE OS_STK * CreateStack(void) ;
PRIVATE BOOL Deadlock(int) ;
PRIVATE void Monitor() ;
PRIVATE void Thread() ;
PRIVATE OS_EVENT * semaphore[RESOURCES] ;
PRIVATE THREAD_STATE thread_state[THREADS] ;
PRIVATE BOOL pending[THREADS][RESOURCES] ;
PRIVATE BOOL acquired[THREADS][RESOURCES] ;
PRIVATE BOOL waiting[THREADS][THREADS] ;
PRIVATE unsigned executions[THREADS] ;
int main()
{
int resource, priority ;
srandom((int) CPU_Clock_Cycles()) ;
ClearScreen(0x07) ;
SetCursorVisible(FALSE) ;
OSInit() ;
for (resource = 0; resource < RESOURCES; resource++)
{
semaphore[resource] = OSSemCreate(1) ;
}
for (priority = 0; priority < THREADS; priority++)
{
OSTaskCreate(Thread, NULL, CreateStack(), priority) ;
}
OSTaskCreate(Monitor, NULL, CreateStack(), priority) ;
OSStart() ;
return 0 ;
}
BOOL Acquire1Resource(int thread, int resource)
{
if (!acquired[thread][resource])
{
BYTE8 err ;
OSSemPend(semaphore[resource], 1, &err) ;
OSTimeDly(random() % 50) ;
if (err != OS_NO_ERR)
{
pending[thread][resource] = TRUE ;
thread_state[thread] = PENDING ;
return FALSE ;
}
acquired[thread][resource] = TRUE ;
pending[thread][resource] = FALSE ;
return TRUE ;
}
return FALSE ;
}
void Release1Resource(int thread, int resource)
{
OSSemPost(semaphore[resource]) ;
acquired[thread][resource] = FALSE ;
}
PRIVATE void Thread(void)
{
static int threads = 0 ;
int thread = threads++ ;
executions[thread] = 0 ;
for (;;)
{
DWORD32 timer ;
thread_state[thread] = SLEEPING ;
OSTimeDly(random() % 1000) ;
AcquireResources(thread, RESOURCES) ;
thread_state[thread] = RUNNING ;
/* Simulate doing some work for up to 1 sec */
timer = OSTimeGet() + (random() % 1000) ;
while (OSTimeGet() < timer) OSTimeDly(1) ;
ReleaseResources(thread, RESOURCES) ;
++executions[thread] ;
}
}
PRIVATE void Analyze(void)
{
int t1, t2, r ;
memset(waiting, FALSE, sizeof(waiting)) ;
for (r = 0; r < RESOURCES; r++)
{
for (t2 = 0; t2 < THREADS; t2++)
{
if (!acquired[t2][r]) continue ;
for (t1 = 0; t1 < THREADS; t1++)
{
if (!pending[t1][r]) continue ;
waiting[t1][t2] = TRUE ;
}
break ;
}
}
}
PRIVATE BOOL Deadlock(int thread)
{
int t1, t2, cycles ;
if (thread_state[thread] != PENDING) return FALSE ;
t1 = thread ;
for (cycles = 0; cycles < THREADS; cycles++)
{
for (t2 = 0; t2 < THREADS; t2++)
{
if (waiting[t1][t2]) break ;
}
if (t2 == THREADS) return FALSE ;
if (t2 == thread) break ;
t1 = t2 ;
}
return TRUE ;
}
PRIVATE void Monitor(void)
{
# define THREAD_SPACING 10
int thread, resource, row, col, row1, col1 ;
SetCursorPosition(24, 35) ;
PutString("Updates: ") ;
row1 = (25 - (6 + 2 * RESOURCES)) / 2 ;
col1 = (80 - (13 + THREAD_SPACING * THREADS)) / 2 ;
row = row1 ;
col = col1 + 14 ;
for (thread = 0; thread < THREADS; thread++)
{
SetCursorPosition(row1, col) ;
PutString("Thread ") ;
PutUnsigned(thread + 1, 10, 0) ;
col += THREAD_SPACING ;
}
SetCursorPosition(row += 2, col1) ;
PutString("Executions:") ;
SetCursorPosition(row += 2, col1) ;
PutString(" State:") ;
for (resource = 0; resource < RESOURCES; resource++)
{
SetCursorPosition(row += 2, col1) ;
PutString("Resource ") ;
PutUnsigned(resource + 1, 10, 0) ;
PutString(":") ;
}
for (;;)
{
static unsigned counter = 0 ;
static char *states[] =
{
"DORMANT ",
"PENDING ",
"READY ",
"RUNNING ",
"SLEEPING"
} ;
OSSchedLock() ;
SetCursorPosition(24, 44) ;
PutUnsigned(++counter, 10, 0) ;
row = row1 + 2 ;
col = col1 + 18 ;
for (thread = 0; thread < THREADS; thread++)
{
SetCursorPosition(row, col) ;
PutUnsigned(executions[thread], 10, 0) ;
col += THREAD_SPACING ;
}
row += 2 ;
col = col1 + 15 ;
Analyze() ;
for (thread = 0; thread < THREADS; thread++)
{
SetCursorPosition(row, col) ;
if (Deadlock(thread)) PutString("DEADLOCK") ;
else PutString(states[thread_state[thread]]) ;
col += THREAD_SPACING ;
}
for (resource = 0; resource < RESOURCES; resource++)
{
row += 2 ;
col = col1 + 15 ;
for (thread = 0; thread < THREADS; thread++)
{
SetCursorPosition(row, col) ;
if (acquired[thread][resource])
PutString("ACQUIRED") ;
else if (pending[thread][resource])
PutString("PENDING ") ;
else
PutString(" ") ;
col += THREAD_SPACING ;
}
}
OSSchedUnlock() ;
OSTimeDly(50) ;
}
}
PRIVATE OS_STK *CreateStack(void)
{
OS_STK *top = (OS_STK *) malloc(STACK_SIZE) + STACK_SIZE ;
if (!top) for (;;) ;
return top ;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -