RTT这个RTOS虽然是全部是用C编写,但全程使用的都是面向对象的编程方式。所以最好的研究方式,就是从对象入手,分析代码各部分所包含的对象以及对象的方法函数。
首先先了解下与thread相关的对象,主要有三个:
1、RTT最基本的对象:rt_object
2、线程对象:rt_thread
3、定时器对象:rt_
timer
这里发现一个现象,按正常逻辑来说rt_thread应该和rt_timer一样,有一个成员直接是rt_object,这样就是明显的继承关系,但是实际代码中rt_thread中申明了和rt_object相同的一组成员:
name,type,flag,以及list这里和其他类的不统一具体原因还需要之后继续研究,这不能说是个bug,只能算是代码风格上的一点不统一。
先从rt_object的成员说起:
rt_object(基本版),这个说明下什么叫做基本版,来看下代码:
```struct rt_object
{
char name[RT_NAME_MAX]; /《 name of kernel object */
rt_uint8_t type; /《 type of kernel object /
rt_uint8_t flag; /**《 flag of kernel object /
ifdef RT_USING_MODULE
void *module_id; /**《 id of application module */
endif
rt_list_t list; /**《 list node of kernel object */
};
typedef struct rt_object rt_object_t; /**《 Type for kernel objects. /```
一个类的声明中有一些成员会因为一些宏定义而增加,这些宏一般代表的是功能的扩展。现在我想分析的是不带最基本的类的成员,所以暂时会去掉所有的宏定义。
可以看到rt_object主要包含4个成员:
1.字符串name,既类的名字。
2.类型type,既类的类型,RTT定义如下12种类型:
enum rt_object_class_type { RT_Object_Class_Thread = 0, /**《 The object is a thread. */ RT_Object_Class_Semaphore, /**《 The object is a semaphore. */ RT_Object_Class_Mutex, /**《 The object is a mutex. */ RT_Object_Class_Event, /**《 The object is a event. */ RT_Object_Class_MailBox, /**《 The object is a mail box. */ RT_Object_Class_MessageQueue, /**《 The object is a message queue. */ RT_Object_Class_MemHeap, /**《 The object is a memory heap */ RT_Object_Class_MemPool, /**《 The object is a memory pool. */ RT_Object_Class_Device, /**《 The object is a device */ RT_Object_Class_Timer, /**《 The object is a timer. */ RT_Object_Class_Module, /**《 The object is a module. */ RT_Object_Class_Unknown, /**《 The object is unknown. */ RT_Object_Class_Static = 0x80 /**《 The object is a static object. */ };
3.标志flag(好像并没什么用,只是在动态创建的时候置0了)。
4.一个双向链表的数据结构,用来把实例化的类添加到相应type的双向链表中。在rt_object初始化时,每种类型的class都有一个链表结构将他们连接起来。
与rt_object相关的函数
RTT中基本上对应class的函数就在相应名字的.c文件中,例如object相关函数就在object.c文件中。
void rt_system_object_init(void); struct rt_object_information * rt_object_get_information(enum rt_object_class_type type); void rt_object_init(struct rt_object *object, enum rt_object_class_type type, const char *name); void rt_object_detach(rt_object_t object); rt_object_t rt_object_allocate(enum rt_object_class_type type, const char *name); void rt_object_delete(rt_object_t object); rt_bool_t rt_object_is_systemobject(rt_object_t object); rt_uint8_t rt_object_get_type(rt_object_t object); rt_object_t rt_object_find(const char *name, rt_uint8_t type);
1.object初始化函数,object初始化有两个函数,分别对应使用静态内存的object初始化,和动态分配内存的object初始化。
void rt_object_init(struct rt_object *object, enum rt_object_class_type type, const char *name); rt_object_t rt_object_allocate(enum rt_object_class_type type, const char *name);
在初始化函数中主要做以下几件事情:
1、为object申请内存(若使用动态初始化)
2、设置object的type成员为指定的类型
3、为object的name成员赋值
4、调用rt_object_attach_hook钩子函数
5、将object加入对应type的container双向链表中
有一点区别需要提出,在voidrt_object_init();中,没有对object的flag成员进行赋值。
```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;
ifdef RT_USING_MODULE
struct rt_dlmodule *module = dlmodule_self();
endif
RT_DEBUG_NOT_IN_INTERRUPT;
/* get object information */
information = rt_object_get_information(type);
RT_ASSERT(information != RT_NULL);
/**申请内存**/
object = (struct rt_object )RT_KERNEL_MALLOC(information-》object_size);
if (object == RT_NULL)
{
/ no memory can be allocated */
return RT_NULL;
}
/* clean memory data of object */
rt_memset(object, 0x0, information-》object_size);
/*/
/* initialize object‘s parameters */
/*初始化成员**/
/ set object type /
object-》type = type;
/* set object flag */
object-》flag = 0;
/* 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();
ifdef RT_USING_MODULE
if (module)
{
rt_list_insert_after(&(module-》object_list), &(object-》list));
object-》module_id = (void *)module;
}
else
endif
{
/* 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;
}```
2、object删除以及detach
只有动态创建的object才能被删除,静态创建的object通过detach脱离object system。
删除/detach object主要完成以下动作:
1、执行rt_object_detach_hook钩子函数
2、将type重置为0
3、将object从对应的双向链表中删除
4、释放分配的内存(动态创建的object)
```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));
/*/
/* reset object type */
object-》type = 0;
/**移出链表*/
/ lock interrupt /
temp = rt_hw_interrupt_disable();
/* remove from old list */
rt_list_remove(&(object-》list));
/* unlock interrupt */
rt_hw_interrupt_enable(temp);
/*/
/**释放内存*/
/ free the memory of object /
RT_KERNEL_FREE(object);
/*/
}```
3、其他与object相关函数。
还有几个与object相关的函数放在一起来说:
(1)void rt_system_object_init(void);
(1)号函数是个空函数,没有被实现
(2)号函数的功能是找到对应class type的双向链表结构,在object初始化中被调用
(3)号函数查询object的type位,以此判断指针指向的是否为object对象
(4)号函数返回object的type成员,返回的对象不包含RT_Object_Class_Static标志
(5)号函数可以在对应的object type中通过name成员寻找对应的object对象,并返回。
原作者:yushigengyu