标签:
基于MQX的应用编程:
通过任务模板定义用户任务,MQX_AUTO_START_TASK -- 任务随MQX一起启动;
/*MQX通过下面的代码(任务模板),向系统注册多个用户进程:--- 当然,我们也可以通过MQX的接口函数来创建任务。*/ const TASK_TEMPLATE_STRUCT MQX_template_list[] = { /* Task Index, Function, Stack, Priority, Name, Attributes, Param, Time Slice */ {SDCARD_TASK,sdcard_task,2000,11,"SDcard",MQX_AUTO_START_TASK,0, 0 }, { 0 } };
(*)MQX实际上也是有main()函数的 -- 在/mqx/source/bsp/<board_name>/Mqx_main.c 中:
int main( void ) { /* Body */ extern const MQX_INITIALIZATION_STRUCT MQX_init_struct; /* Start MQX */ _mqx( (MQX_INITIALIZATION_STRUCT_PTR) &MQX_init_struct );
return 0; } /* Endbody */
(*)/mqx/source/bsp/<board_name>/Mqx_init.c 文件:
extern TASK_TEMPLATE_STRUCT MQX_template_list[]; const MQX_INITIALIZATION_STRUCT MQX_init_struct = { /* PROCESSOR_NUMBER */ BSP_DEFAULT_PROCESSOR_NUMBER, /* START_OF_KERNEL_MEMORY */ BSP_DEFAULT_START_OF_KERNEL_MEMORY, /* END_OF_KERNEL_MEMORY */ BSP_DEFAULT_END_OF_KERNEL_MEMORY, /* INTERRUPT_STACK_SIZE */ BSP_DEFAULT_INTERRUPT_STACK_SIZE, /* TASK_TEMPLATE_LIST */ MQX_template_list, /* MQX_HARDWARE_INTERRUPT_LEVEL_MAX*/ BSP_DEFAULT_MQX_HARDWARE_INTERRUPT_LEVEL_MAX, /* MAX_MSGPOOLS */ BSP_DEFAULT_MAX_MSGPOOLS, /* MAX_MSGQS */ BSP_DEFAULT_MAX_MSGQS, /* IO_CHANNEL */ BSP_DEFAULT_IO_CHANNEL, /* IO_OPEN_MODE */ BSP_DEFAULT_IO_OPEN_MODE, 0, 0, #if MQX_ENABLE_USER_MODE BSP_DEFAULT_START_OF_KERNEL_AREA, BSP_DEFAULT_END_OF_KERNEL_AREA, BSP_DEFAULT_START_OF_USER_DEFAULT_MEMORY, BSP_DEFAULT_END_OF_USER_DEFAULT_MEMORY, BSP_DEFAULT_START_OF_USER_HEAP, BSP_DEFAULT_END_OF_USER_HEAP, BSP_DEFAULT_START_OF_USER_RW_MEMORY, BSP_DEFAULT_END_OF_USER_RW_MEMORY, BSP_DEFAULT_START_OF_USER_RO_MEMORY, BSP_DEFAULT_END_OF_USER_RO_MEMORY, BSP_DEFAULT_START_OF_USER_NO_MEMORY, BSP_DEFAULT_END_OF_USER_NO_MEMORY, BSP_DEFAULT_MAX_USER_TASK_PRIORITY, BSP_DEFAULT_MAX_USER_TASK_COUNT, #endif };
(*) _mqx()函数 -- 在/mqx/source/kernel/Mqx.c 中(下面的代码,删除了所有条件编译的部分):
/*! * \brief Initializes and starts MQX on the processor. * * The function does the following: * \li Initializes the default memory pool and memory components. * \li Initializes kernel data. * \li Performs BSP-specific initialization, which includes installing the * periodic timer. * \li Performs PSP-specific initialization. * \li Creates the interrupt stack. * \li Creates the ready queues. * \li Starts MQX tasks. * \li Starts autostart application tasks. * * \param[in] mqx_init Pointer to the MQX initialization structure for the * processor. * * \return Does not return (Success.) * \return If application called _mqx_exit(), error code that it passed to * _mqx_exit() (Success.) * \return Errors from _int_install_isr() (MQX cannot install the interrupt * subsystem.) * \return Errors from _io_init() (MQX cannot install the I/O subsystem.) * \return Errors from _mem_alloc_system() (There is not enough memory to * allocate either the interrupt stack or the interrupt table.) * \return Errors from _mem_alloc_zero() (There is not enough memory to allocate * the ready queues.) * \return MQX_KERNEL_MEMORY_TOO_SMALL (Init_struct_ptr does not specify enough * kernel memory.) * \return MQX_OUT_OF_MEMORY (There is not enough memory to allocate either the * ready queues, the interrupt stack, or the interrupt table.) * \return MQX_TIMER_ISR_INSTALL_FAIL (MQX cannot install the periodic timer ISR.) * * \warning Must be called exactly once per processor. * * \see _mqx_exit * \see _int_install_isr * \see _mem_alloc() * \see _mem_alloc_from() * \see _mem_alloc_system() * \see _mem_alloc_system_from() * \see _mem_alloc_system_zero() * \see _mem_alloc_system_zero_from() * \see _mem_alloc_zero() * \see _mem_alloc_zero_from() * \see _mem_alloc_align() * \see _mem_alloc_align_from() * \see _mem_alloc_at() * \see MQX_INITIALIZATION_STRUCT * \see TASK_TEMPLATE_STRUCT */ _mqx_uint _mqx( register MQX_INITIALIZATION_STRUCT_PTR mqx_init ) { /* Body */ KERNEL_DATA_STRUCT_PTR kernel_data; TASK_TEMPLATE_STRUCT_PTR template_ptr; /*任务模板指针*/ TD_STRUCT_PTR td_ptr; _mqx_uint result; pointer stack_ptr; pointer sys_td_stack_ptr; uchar_ptr sys_stack_base_ptr; /* * The kernel data structure starts at the start of kernel memory, * as specified in the initialization structure. Make sure address * specified is aligned */ kernel_data = (KERNEL_DATA_STRUCT_PTR) _ALIGN_ADDR_TO_HIGHER_MEM(mqx_init->START_OF_KERNEL_MEMORY); /* Set the global pointer to the kernel data structure */ _SET_KERNEL_DATA(kernel_data); /* The following assignments are done to force the linker to include * the symbols, which are required by TAD. * Note that we should use address of the variable so it is not optimized * as direct constant assignment when optimization level is high. * Note that counter will be immediately reset to zero on the subsequent * _mem_zero call. */ *(volatile pointer*) kernel_data = (pointer) & _mqx_version_number; *(volatile pointer*) kernel_data = (pointer) & _mqx_vendor; /* Initialize the kernel data to zero. */ _mem_zero((pointer) kernel_data, (_mem_size) sizeof(KERNEL_DATA_STRUCT)); /* Copy the MQX initialization structure into kernel data. */ kernel_data->INIT = *mqx_init; kernel_data->INIT.START_OF_KERNEL_MEMORY = (pointer) kernel_data; kernel_data->INIT.END_OF_KERNEL_MEMORY = (pointer) _ALIGN_ADDR_TO_LOWER_MEM(kernel_data->INIT.END_OF_KERNEL_MEMORY); /* init kernel data structures */ _mqx_init_kernel_data_internal(); /* Initialize the memory resource manager for the kernel */ result = _mem_init_internal(); /* * Set the stack for the system TD, in case the idle task gets blocked * by an exception or if idle task is not used. */ result = PSP_MINSTACKSIZE; sys_td_stack_ptr = _mem_alloc_system((_mem_size) result); _mem_set_type(sys_td_stack_ptr, MEM_TYPE_SYSTEM_STACK); sys_stack_base_ptr = (uchar_ptr) _GET_STACK_BASE(sys_td_stack_ptr, result); td_ptr = SYSTEM_TD_PTR(kernel_data); td_ptr->STACK_PTR = (pointer)(sys_stack_base_ptr - sizeof(PSP_STACK_START_STRUCT)); td_ptr->STACK_BASE = sys_stack_base_ptr; _mqx_system_stack = td_ptr->STACK_PTR; /* Build the MQX ready to run queues */ result = _psp_init_readyqs(); /* Create a light wait semaphore for task creation/destruction creation */ _lwsem_create((LWSEM_STRUCT_PTR) & kernel_data->TASK_CREATE_LWSEM, 1); /* Call bsp to enable timers and other devices */ result = _bsp_enable_card(); /* Check here for auto-create tasks, and create them here */ /*加载用户任务列表*/ template_ptr = kernel_data->INIT.TASK_TEMPLATE_LIST; while (template_ptr->TASK_TEMPLATE_INDEX) { if (template_ptr->TASK_ATTRIBUTES & MQX_AUTO_START_TASK) { /*检测任务属性*/ td_ptr = _task_init_internal( /*创建任务,返回任务描述符*/ template_ptr, /*任务列表指针*/ kernel_data->ACTIVE_PTR->TASK_ID, template_ptr->CREATION_PARAMETER, FALSE, NULL, 0 ); #if MQX_CHECK_MEMORY_ALLOCATION_ERRORS if (td_ptr == NULL) { _mqx_exit(MQX_OUT_OF_MEMORY); } /* Endif */ #endif _task_ready_internal(td_ptr); /*把任务加入运行队列*/ } /* Endif */ ++template_ptr; /*指针加1 */ } /* Endwhile */ _sched_start_internal(); /* WILL NEVER RETURN FROM HERE */ return MQX_OK; /* To satisfy lint */ } /* Endbody */
标签:
原文地址:http://www.cnblogs.com/nju347/p/4271753.html