您的位置:首页 > 其它

[RT-Thread 源码分析] 3. 内核对象管理

2013-04-22 11:09 411 查看
RTT在设计时虽然采用了c语言,但使用了面向对象的思想。所有的线程、事件设备等都是继承自object,且采用链表的方式统一管理。如图所示。



对象控制块
/**
* Base structure of Kernel object
*/
struct rt_object
{
char       name[RT_NAME_MAX];   // 名称
rt_uint8_t type;                // 内核对象类型
rt_uint8_t flag;                // 内核对象标志

#ifdef RT_USING_MODULE
void      *module_id;           // 模块ID
#endif
rt_list_t  list;                // 内核对象链表节点
};
typedef struct rt_object *rt_object_t;
在内核里,所有对象都由链表组织起来。链表定义如下:
struct rt_list_node
{
struct rt_list_node *next; // 指向下一节点
struct rt_list_node *prev; // 指向前一节点
};
typedef struct rt_list_node rt_list_t;
所有可能派生出来的对象为:
/**
*  The object type can be one of the follows with specific
*  macros enabled:
*  - Thread
*  - Semaphore
*  - Mutex
*  - Event
*  - MailBox
*  - MessageQueue
*  - MemHeap
*  - MemPool
*  - Device
*  - Timer
*  - Module
*  - Unknown
*  - Static
*/
enum rt_object_class_type
{
RT_Object_Class_Thread = 0,     // 线程
#ifdef RT_USING_SEMAPHORE
RT_Object_Class_Semaphore,      // 信号量
#endif
#ifdef RT_USING_MUTEX
RT_Object_Class_Mutex,          // 互斥锁
#endif
#ifdef RT_USING_EVENT
RT_Object_Class_Event,          // 事件
#endif
#ifdef RT_USING_MAILBOX
RT_Object_Class_MailBox,        // 邮箱
#endif
#ifdef RT_USING_MESSAGEQUEUE
RT_Object_Class_MessageQueue,   // 消息队列
#endif
#ifdef RT_USING_MEMHEAP
RT_Object_Class_MemHeap,        // 内存堆
#endif
#ifdef RT_USING_MEMPOOL
RT_Object_Class_MemPool,        // 内存池
#endif
#ifdef RT_USING_DEVICE
RT_Object_Class_Device,         // 设备驱动
#endif
RT_Object_Class_Timer,          // 时钟
#ifdef RT_USING_MODULE
RT_Object_Class_Module,         // 模块
#endif
RT_Object_Class_Unknown,        // 未知内核对象类型
RT_Object_Class_Static = 0x80   // rt-thread以此位标志是否为系统内核对象
};
所有对象又被放置于对象容器中:
/**
* The information of the kernel object
*/
struct rt_object_information
{
enum rt_object_class_type type;          // 内核对象类型
rt_list_t                 object_list;   // 内核对象链表
rt_size_t                 object_size;   // 内核对象所占的大小
};

RTT中,内核对象管理系统是用一个rt_object_information数组来实现的,如下:
#define _OBJ_CONTAINER_LIST_INIT(c)\
// 内核对象容器的链表初始化,这里用一个宏来定义,链表的前一节点和后一节点在初始化时都指向本身所在地址
{&(rt_object_container[c].object_list), &(rt_object_container[c].object_list)}

//内核对象管理系统,这里用rt_object_information数组来实现
struct rt_object_information rt_object_container[RT_Object_Class_Unknown] =
{
/* initialize object container - thread */)},//线程对象信息
{RT_Object_Class_Thread, _OBJ_CONTAINER_LIST_INIT(RT_Object_Class_Thread), sizeof(struct rt_thread#ifdef RT_USING_SEMAPHORE
/* initialize object container - semaphore *///信号量对象信息
{RT_Object_Class_Semaphore, _OBJ_CONTAINER_LIST_INIT(RT_Object_Class_Semaphore), sizeof(struct rt_semaphore)},
#endif
#ifdef RT_USING_MUTEX
/* initialize object container - mutex *///互斥锁对象信息
{RT_Object_Class_Mutex, _OBJ_CONTAINER_LIST_INIT(RT_Object_Class_Mutex), sizeof(struct rt_mutex)},
#endif
#ifdef RT_USING_EVENT
/* initialize object container - event *///事件对象信息
{RT_Object_Class_Event, _OBJ_CONTAINER_LIST_INIT(RT_Object_Class_Event), sizeof(struct rt_event)},
#endif
#ifdef RT_USING_MAILBOX
/* initialize object container - mailbox *///邮箱对象信息
{RT_Object_Class_MailBox, _OBJ_CONTAINER_LIST_INIT(RT_Object_Class_MailBox), sizeof(struct rt_mailbox)},
#endif
#ifdef RT_USING_MESSAGEQUEUE
/* initialize object container - message queue *///消息队列对象信息
{RT_Object_Class_MessageQueue, _OBJ_CONTAINER_LIST_INIT(RT_Object_Class_MessageQueue), sizeof(struct rt_messagequeue)},
#endif
#ifdef RT_USING_MEMHEAP
/* initialize object container - memory heap *///内存堆对象信息
{RT_Object_Class_MemHeap, _OBJ_CONTAINER_LIST_INIT(RT_Object_Class_MemHeap), sizeof(struct rt_memheap)},
#endif
#ifdef RT_USING_MEMPOOL
/* initialize object container - memory pool *///内存池对象信息
{RT_Object_Class_MemPool, _OBJ_CONTAINER_LIST_INIT(RT_Object_Class_MemPool), sizeof(struct rt_mempool)},
#endif
#ifdef RT_USING_DEVICE
/* initialize object container - device *///设备驱动对象信息
{RT_Object_Class_Device, _OBJ_CONTAINER_LIST_INIT(RT_Object_Class_Device), sizeof(struct rt_device)},
#endif
/* initialize object container - timer *///时钟对象信息
{RT_Object_Class_Timer, _OBJ_CONTAINER_LIST_INIT(RT_Object_Class_Timer), sizeof(struct rt_timer)},
#ifdef RT_USING_MODULE
/* initialize object container - module *///模块对象信息
{RT_Object_Class_Module, _OBJ_CONTAINER_LIST_INIT(RT_Object_Class_Module), sizeof(struct rt_module)},
#endif
};

1. 内核对象初始化
=====
初始化分为静态和动态,区别主要静态是编译时确定,线程栈就在堆栈上,而动态则是运行时确定,其栈在堆上。
/**
* This function will initialize an object and add it to object system
* management.
*
* @param object the specified object to be initialized.
* @param type the object type.
* @param name the object name. In system, the object's name must be unique.
*/
void rt_object_init(struct rt_object         *object,   // 指向已存在的对象指针
enum rt_object_class_type type,     // 对象的类型
const char               *name)     // 对象的名字字符串
{
register rt_base_t temp;
struct rt_object_information *information;      // 对象容器

#ifdef RT_USING_MODULE
/* get module object information */
information = (rt_module_self() != RT_NULL) ?
&rt_module_self()->module_object[type] : &rt_object_container[type];
#else
/* get object information */
// 从对象容器数组中,获取该类对象的链表信息
information = &rt_object_container[type];
#endif

/* initialize object's parameters */

/* set object type to static */
// 将对象置位静态
object->type = type | RT_Object_Class_Static;

/* copy name */
// 复制名字,字符串,并且规定字符串长度
rt_strncpy(object->name, name, RT_NAME_MAX);

RT_OBJECT_HOOK_CALL(rt_object_attach_hook, (object));

/* lock interrupt */
// 禁中断
temp = rt_hw_interrupt_disable();

/* insert object into information object list */
// 将新对象插入当前对象容器中的链表
rt_list_insert_after(&(information->object_list), &(object->list));

/* unlock interrupt */
// 开中断
rt_hw_interrupt_enable(temp);
}

2. 线程脱离
/**
* This function will detach a static object from object system,
* and the memory of static object is not freed.
*
* @param object the specified object to be detached.
*/
void rt_object_detach(rt_object_t object)
{
register rt_base_t temp;

/* object check */
RT_ASSERT(object != RT_NULL);

RT_OBJECT_HOOK_CALL(rt_object_detach_hook, (object));

/* lock interrupt */
temp = rt_hw_interrupt_disable();

/* remove from old list */
// 将对象从链表中删除
// 因为这是静态的对象方法,所以并不是真正的将对象删除,只是将其移除链表
// 其所占的内存空间也不会回收
rt_list_remove(&(object->list));

/* unlock interrupt */
rt_hw_interrupt_enable(temp);
}

3. 动态初始化
=====
#ifdef RT_USING_HEAP
/**
* This function will allocate an object from object system
*
* @param type the type of object
* @param name the object name. In system, the object's name must be unique.
*
* @return object
*/
rt_object_t rt_object_allocate(enum rt_object_class_type type, const char *name)
// 由于是动态的,只需传入类型和名字。其内存空间是在函数中动态分配的
{
struct rt_object *object;
register rt_base_t temp;
struct rt_object_information *information;

RT_DEBUG_NOT_IN_INTERRUPT;

#ifdef RT_USING_MODULE
/*
* get module object information,
* module object should be managed by kernel object container
*/
information = (rt_module_self() != RT_NULL && (type != RT_Object_Class_Module)) ?
&rt_module_self()->module_object[type] : &rt_object_container[type];
#else
/* get object information */
information = &rt_object_container[type];
#endif

object = (struct rt_object *)rt_malloc(information->object_size);
// 按照其所要求的空间在heap上动态分配内存空间
if (object == RT_NULL)
{
/* no memory can be allocated */
return RT_NULL;
}
// 其后的步骤就和静态类似

/* initialize object's parameters */

/* set object type */
object->type = type;

/* set object flag */
object->flag = 0;

#ifdef RT_USING_MODULE
if (rt_module_self() != RT_NULL)
{
object->flag |= RT_OBJECT_FLAG_MODULE;
}
object->module_id = (void *)rt_module_self();
#endif

/* copy name */
rt_strncpy(object->name, name, RT_NAME_MAX);

RT_OBJECT_HOOK_CALL(rt_object_attach_hook, (object));

/* lock interrupt */
temp = rt_hw_interrupt_disable();

/* insert object into information object list */
rt_list_insert_after(&(information->object_list), &(object->list));

/* unlock interrupt */
rt_hw_interrupt_enable(temp);

/* return object */
return object;
}

4. 动态线程删除
=====
/**
* This function will delete an object and release object memory.
*
* @param object the specified object to be deleted.
*/
void rt_object_delete(rt_object_t object)
{
register rt_base_t temp;

/* object check */
RT_ASSERT(object != RT_NULL);
RT_ASSERT(!(object->type & RT_Object_Class_Static));
// 断言,确保不是静态

RT_OBJECT_HOOK_CALL(rt_object_detach_hook, (object));

/* lock interrupt */
temp = rt_hw_interrupt_disable();

/* remove from old list */
// 首先从链表中删除
rt_list_remove(&(object->list));

/* unlock interrupt */
rt_hw_interrupt_enable(temp);

#if defined(RT_USING_MODULE) && defined(RT_USING_SLAB)
if (object->flag & RT_OBJECT_FLAG_MODULE)
rt_module_free((rt_module_t)object->module_id, object);
else
#endif

/* free the memory of object */
// 由于是动态,还需释放其所占的空间
rt_free(object);
}
#endif
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: