ct_os.c

来自「DVB软件,基于CT216软件的开发源程序.」· C语言 代码 · 共 465 行

C
465
字号
/*
 * ct_os.c
 *
 * Copyright (C) 2005 Cheertek Inc, K300 all right reserved.
 *
 * Nov 22, 2005 file created by K300 (Mark Lu).
 *
 * CT OS API.
 */
#include <stdio.h>
#include <string.h>
#include <stdlib.h>

#include "ct_os.h"

#include "cyg/kernel/kapi.h"
#include "cyg/memalloc/kapi.h"

#include "ct_type.h"
#include "ct_config.h"
#include "ct_uart.h"
#include "ct_sys.h"
#include "ct_irq.h"
/*******************************************************************************************/
#if 0
#define OS_MSG(p)
#else
#define OS_MSG(p)			printf p
#endif

#if 1
#define OS_DBG(p)
#else
#define OS_DBG(p) 		printf p
#endif

//#define CT_OS_INT_DEBUG
//#define CT_OS_MEM_DEBUG
//#define CT_OS_MEM_LOG

//#define EXTRA_SEMAPHORE_INFO
#define DUMP_SEM_WAIT_IN_DSR

#define TRY_DELAY 0 // ms or 0 for disable try function.
//#define TASK_TRACKING

/*******************************************************************************************/
#define CT_OS_VERSION					"1.00a"

//#include "hw_config.h"

#define CT_OS_MIN_QUEUE_SLOT (CYGNUM_KERNEL_SYNCH_MBOX_QUEUE_SIZE)

#ifdef CT_OS_INT_DEBUG
#define REG_PLAT_TIMER4_CTRL              (*((vu32 *) (0x80000000+0x070)))   // 0070
#define REG_PLAT_TIMER4_VALUE             (*((vu32 *) (0x80000000+0x074)))   // 0074
#define CT_OS_INFO_MAX_IDX              200
typedef struct
{
	u8		u8Vector1;
	u8		u8Vector2;

	u32		u32IsrTimeStart;
	u32		u32IsrTime;

	u32		u32DsrTimeStart;
       u32         u32DsrTime;

       u32         u32IsrTimeStop;
       u32         u32DsrTimeStop;

} CT_OS_INT_INFO;
CT_OS_INT_INFO stOSIntInfo[200];
u16 u16InfoWIdx = 0;
u16 u16InfoRIdx = 0;
u8 u8OsInfoStack[4096];
CTOS_TASK tOsInfo;
#endif

#define CT_OS_MEMPOOL_MAX_NUM		10
#define CT_OS_TASK_MAX_NUM			50
#define CT_OS_PRI_ISR_MAX_NUM		16
#define CT_OS_SEC_ISR_MAX_NUM		16
#define CT_OS_SEC2_ISR_MAX_NUM		24
#if defined(CT216S) || defined(CT216T) ||defined(CT216H)
#define CT_OS_SEC3_ISR_MAX_NUM		16
#endif

#define CT_OS_TIMER_MAX_NUM			35
#define CT_OS_QUEUE_MAX_NUM         40
#define CT_OS_SEMAPHORE_MAX_NUM		70

#define CTOS_MIN_ALLOCATE_SIZE		4
#define CTOS_DRAM_START_ADDR		0x40000000

/* Thread State Information */
#define CYG_THREAD_RUNNING     0          // Thread is runnable or running
#define CYG_THREAD_SLEEPING    1          // Thread is waiting for something to happen
#define CYG_THREAD_COUNTSLEEP  2          // Sleep in counted manner
#define CYG_THREAD_SUSPENDED   4          // Suspend count is non-zero
#define CYG_THREAD_CREATING    8          // Thread is being created
#define CYG_THREAD_EXITED      16         // Thread has exited

#define SEMAPHORE_NAME_LEN  12
#define SEMAPHORE_WAIT_TASK 20


#ifdef CT_OS_CHECK_STACKSIZE
#undef CT_OS_CHECK_STACKSIZE
#endif

#ifdef ONE_TICK_ONE_MILLISTION_SECOND_USED
#define CTOS_TICK_PER_MS			1
#endif /* end #ifdef ONE_TICK_ONE_MILLISTION_SECOND_USED */

#ifdef CT_OS_MEM_LOG
#define MEM_LOG_NUM		100
#define MEM_USER_MEM	16
typedef enum
{
	EN_POOL_SIZE=0,
	EN_POOL_TIME,
	EN_POOL_NUM
};
u16	u16MemLogNum;
u32 au32MemLog[CT_OS_MEMPOOL_MAX_NUM][EN_POOL_NUM][MEM_LOG_NUM];			// Pool name .	Alloc Size  . Num
u8	u8ShowMsg;
#endif
typedef struct QUEUE_INFORMATION
{
	u32 u32QueueHandle;
	u32* pu32StartAddr;
	u32 u32DWSize;
	cyg_mbox mbox;
	u32 u32QueueID;
	u32 u32MsgSizeDW;
	u32 au32MsgAllocated[CT_OS_MIN_QUEUE_SLOT/32];
} CT_QUEUE_INFO;

CT_QUEUE_INFO stQueueInfo[CT_OS_QUEUE_MAX_NUM];

typedef struct MEMORY_INFORMATION
{
	u32 u32MemPoolHandle;
	u8 au8PoolName [CTOS_MAX_NAME + 1];
	void *pStartAddr;
	u32 u32Size;
	cyg_mempool_var var;
} CT_MEMORY_INFO;

CT_MEMORY_INFO stMemPoolInfo[CT_OS_MEMPOOL_MAX_NUM];

typedef struct TASK_INFORMATION
{
	u32 u32TaskHandle;
	u8 task_name [CTOS_MAX_NAME + 1];
	CTOS_TASK_ENTRY_FN fnTaskEntryFun;
	u32 u32Argc;
	void *pArgv;
	cyg_thread producer_thread;
} CT_TASK_INFO;

typedef struct TASK_MONITOR_INFO
{
	u32 u32TaskHandle;
	u8 task_name [CTOS_MAX_NAME + 1];
	u32 u32scheduled_count;
	u32 u32TaskID;
} CT_TASK_MONITOR_INFO;

CT_TASK_MONITOR_INFO stTaskMonitorInfo[CT_OS_TASK_MAX_NUM];
CT_TASK_INFO stTaskInfo[CT_OS_TASK_MAX_NUM];

typedef struct ISR_INFORMATION
{
	CTOS_LISR_ENTRY_FN fnISREntryFun;
	CTOS_HISR_ENTRY_FN fnDSREntryFun;
	u32 u32ISRVector;
	u32 u32ISRHandle;
	bool8 b8DSRFlag;
	cyg_interrupt intr;
} CT_ISR_INFO;

CT_ISR_INFO stISRInfo[CT_OS_PRI_ISR_MAX_NUM];

typedef struct SEC_ISR_INFORMATION
{
	CTOS_LISR_ENTRY_FN fnISREntryFun;
	CTOS_HISR_ENTRY_FN fnDSREntryFun;
//	bool8 b8DSRRun;
	u32 u32DSRCounter;
} CT_SEC_ISR_INFO;

CT_SEC_ISR_INFO stSecISRInfo[CT_OS_SEC_ISR_MAX_NUM];
CT_SEC_ISR_INFO stSec2ISRInfo[CT_OS_SEC2_ISR_MAX_NUM];
#if defined(CT216S) || defined(CT216T) ||defined(CT216H)
CT_SEC_ISR_INFO stSec3ISRInfo[CT_OS_SEC3_ISR_MAX_NUM];
#endif


typedef struct TIMER_INFORMATION
{
	u32 u32TimerHandle;
	u32 u32Id;
	CTOS_TIMER_CALLBACK_FN fnTimerEntryFun;
	cyg_alarm alarm;
} CT_TIMER_INFO;

CT_TIMER_INFO stTimerInfo[CT_OS_TIMER_MAX_NUM];

typedef struct SEMAPHORE_INFORMATION
{
    char strSemaphoreName[SEMAPHORE_NAME_LEN];
	u32 u32SemaphoreHandle;
#ifdef EXTRA_SEMAPHORE_INFO
	u32 u32WaitingTaskHandle[SEMAPHORE_WAIT_TASK];
	bool8 b8ObtainedTask[SEMAPHORE_WAIT_TASK];
#endif
} CT_SEMAPHORE_INFO;

CT_SEMAPHORE_INFO stSemaphoreInfo[CT_OS_SEMAPHORE_MAX_NUM];

/************************************************************************
 *
 ************************************************************************/
extern u32 *  END_ADDRESS;
CTOS_MEM_POOL EIT_MEM_POOL;
bool8 bEITPoolUsed = FALSE;  /* record the eit pool used or not */
bool8 bGetHISRInfo = FALSE;
static u32 u32OldLevel = CTOS_ENABLE_INTERRUPTS;
static volatile u32 u32TrackingTaskID = 0xffffffff;
//static u32 u32SdramSize=0;

//CTOS_SEMAPHORE stQueueSemaphore;
//CTOS_SEMAPHORE stMemSemaphore;
//CTOS_SEMAPHORE stTaskSemaphore;
//CTOS_SEMAPHORE stTimerSemaphore;

cyg_handle_t	counter_handle;

static u8 CT_OS_TaskUsageRate(u8 *u8pStackAddr, u32 u32Size);

static CTOS_TIMER OSMonitorTimer;
static bool8 b8OSMonitoring = FALSE;
static u32	u32MonitorCount = 0;
static u32 u32QueueCounter = 0;

static void ResetTaskMonitor (void);
static void BuildTaskMonitor (void);

EN_CTOS_STATUS  CT_OS_Semaphore_Information(CTOS_SEMAPHORE *pSemaphore, u8 *pu8Name,
                  u32 *pu32CurCount, EN_CTOS_SUSPEND_TYPE *penSuspendType,
                  u32 *pu32TaskWaiting, CTOS_TASK **FirstTask);

#ifdef TASK_TRACKING
inline void _task_tracking(void)
{
	cyg_thread* thread_cb;
	cyg_thread_info info;
	bool8 b8TaskTrackingStarted;

	if( u32TrackingTaskID!=0xffffffff )
	{
		thread_cb = cyg_thread_self();
		if( cyg_thread_get_info( thread_cb, thread_cb->unique_id, &info )==TRUE )
		{
			b8TaskTrackingStarted = FALSE;

//			cyg_scheduler_lock();	// register windows will fill with interrupt's stack
			cyg_interrupt_disable();
			while( info.id==(u16)u32TrackingTaskID )
			{
				// waiting for dsu connection
				if( b8TaskTrackingStarted == FALSE)
				{
					b8TaskTrackingStarted = TRUE;
					OS_DBG(("\n  Task %s [ID:%d] is locked, please check callstack by DSU.\n", info.name, info.id));
					OS_DBG(("  then resume problem by wmem 0x%08x 0xffffffff\n", &u32TrackingTaskID));
				}
			}
//			cyg_scheduler_unlock();
			cyg_interrupt_enable();
		}
	}
}
#endif

/************************************************************************
 * debug printf
 ************************************************************************/
#if 0
static void dis_dec_val(u32 u32StackUsage)
{
	CT_UART_PutChar(' ');
//	CT_UART_PutChar((u32StackUsage/100000000)+0x30);
//	u32StackUsage%=100000000;
//	CT_UART_PutChar((u32StackUsage/10000000)+0x30);
//	u32StackUsage%=10000000;
//	CT_UART_PutChar((u32StackUsage/1000000)+0x30);
//	u32StackUsage%=1000000;
	CT_UART_PutChar((u32StackUsage/100000)+0x30);
	u32StackUsage%=100000;
	CT_UART_PutChar((u32StackUsage/10000)+0x30);
	u32StackUsage%=10000;
	CT_UART_PutChar((u32StackUsage/1000)+0x30);
	u32StackUsage%=1000;
	CT_UART_PutChar((u32StackUsage/100)+0x30);
	u32StackUsage%=100;
	CT_UART_PutChar((u32StackUsage/10)+0x30);
	u32StackUsage%=10;
	CT_UART_PutChar((u32StackUsage)+0x30);
	CT_UART_PutChar(' ');
}

static int iii;
static u32 u32Val;
static char num_arr[]={'0', '1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};
static void dis_hex_val(u32 u32StackUsage)
{
	CT_UART_PutChar(' ');
	CT_UART_PutChar('0');
	CT_UART_PutChar('x');
	for ( iii=8; iii>0; iii--)
	{
		u32Val=u32StackUsage>>28;
		CT_UART_PutChar(num_arr[u32Val]);
		u32StackUsage=u32StackUsage<<4;
	}
	CT_UART_PutChar(' ');
}
#endif //#if 0

/************************************************************************
 * Task Convert Callback Function.
 ************************************************************************/

void TaskConvertCallbackFun (cyg_addrword_t data)
{
	if (stTaskInfo[data].fnTaskEntryFun != NULL)
	{
		stTaskInfo[data].fnTaskEntryFun (stTaskInfo[data].u32Argc, stTaskInfo[data].pArgv);
	}
}

/************************************************************************
 * ISR Convert Callback Function.
 ************************************************************************/

cyg_uint32 ISRConvertCallbackFun (cyg_vector_t vector, cyg_addrword_t data)
{
	u32 u32Index;
	bool8 b8CallDSR = FALSE;
	u32 u32Pending;

#if defined(CT216S) || defined(CT216T) || defined(CT216H)
	if (vector == (INTR_3RD_SEC_INT_CTLR - PRI_ITBL_BASE))
	{
        u32Pending = CT_IRQ_Get3ndSecondaryPending();
		for (u32Index = 0; u32Index < CT_OS_SEC3_ISR_MAX_NUM; u32Index++)
		{
			if ((u32Pending >> u32Index) & 1)
			{
				if (stSec3ISRInfo[u32Index].fnISREntryFun != NULL)
				{
#ifdef CT_OS_INT_DEBUG
                                   OS_SetIntInfo(vector, TRUE, TRUE, u32Index);
#endif
					stSec3ISRInfo[u32Index].fnISREntryFun (u32Index);
#ifdef CT_OS_INT_DEBUG
                                   OS_SetIntInfo(vector, FALSE, TRUE, u32Index);
#endif
					if (stISRInfo[vector].u32ISRVector == vector)
					{
						if (stISRInfo[vector].b8DSRFlag == TRUE)
						{
							b8CallDSR = TRUE;
							stSec3ISRInfo[u32Index].u32DSRCounter++;
						}
					}
				}
			}
		}
	}
	else
#endif
	if (vector == (INTR_2ND_SEC_INT_CTLR - PRI_ITBL_BASE))
	{
    	u32Pending = CT_IRQ_Get2ndSecondaryPending();
		for (u32Index = 0; u32Index < CT_OS_SEC2_ISR_MAX_NUM; u32Index++)
		{
			if ((u32Pending >> u32Index) & 1)
			{
				if (stSec2ISRInfo[u32Index].fnISREntryFun != NULL)
				{
#ifdef CT_OS_INT_DEBUG
                                   OS_SetIntInfo(vector, TRUE, TRUE, u32Index);
#endif
					stSec2ISRInfo[u32Index].fnISREntryFun (u32Index);
#ifdef CT_OS_INT_DEBUG
                                   OS_SetIntInfo(vector, FALSE, TRUE, u32Index);
#endif
					if (stISRInfo[vector].u32ISRVector == vector)
					{
						if (stISRInfo[vector].b8DSRFlag == TRUE)
						{
							b8CallDSR = TRUE;
							stSec2ISRInfo[u32Index].u32DSRCounter++;
						}
					}
				}
			}
		}
	}
	else if (vector == (INTR_SEC_INT_CTLR - PRI_ITBL_BASE))
	{
        u32Pending = CT_IRQ_GetSecondaryPending();
		for (u32Index = 0; u32Index < CT_OS_SEC_ISR_MAX_NUM; u32Index++)
		{
			if ((u32Pending >> u32Index) & 1)
			{
				if (stSecISRInfo[u32Index].fnISREntryFun != NULL)
				{
#ifdef CT_OS_INT_DEBUG
                                   OS_SetIntInfo(vector, TRUE, TRUE, u32Index);
#endif
					stSecISRInfo[u32Index].fnISREntryFun (u32Index);
#ifdef CT_OS_INT_DEBUG
                                   OS_SetIntInfo(vector, FALSE, TRUE, u32Index);
#endif
					if (stISRInfo[vector].u32ISRVector == vector)
					{
						if (stISRInfo[vector].b8DSRFlag == TRUE)
						{
							b8CallDSR = TRUE;
							stSecISRInfo[u32Index].u32DSRCounter++;
						}
					}
				}
			}
		}
	}
	else //PRI_ITBL_BASE
	{
			if (stISRInfo[vector].u32ISRVector == vector)
			{
				if (stISRInfo[vector].fnISREntryFun != NULL)
				{
#ifdef CT_OS_INT_DEBUG
                                   OS_SetIntInfo(vector, TRUE, TRUE, 0xFF);
#endif
					stISRInfo[vector].fnISREntryFun (vector);
#ifdef CT_OS_INT_DEBUG
                                   OS_SetIntInfo(vector, FALSE, TRUE, 0xFF);
#endif
					if (stISRInfo[vector].b8DSRFlag == TRUE)
					{
						b8CallDSR = TRUE;
					}
				}
			}
	}

	if (b8CallDSR)
	{
		// reference J code(interrupt.c), ňゎVou_int_line16咀

⌨️ 快捷键说明

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