rt_thread 里面链表的使用

RT_thread 使用链表构架异步通知消息队列

RT_Thread 里面链表的介绍

  • 关于 rt_list_entry
  #define rt_list_entry(node, type, member) \
    rt_container_of(node, type, member)
  #define rt_container_of(ptr, type, member) \
    ((type *)((char *)(ptr) - (unsigned long)(&((type *)0)->member)))

可以看出 rt_list_entry 的作用是先计算链表在其他结构体内的偏移地址,在通过链表的地址偏移地址,就是当前结构体的地址。

/**
 * @brief 蓝牙监听器的类型定义
 */
typedef struct st_bluetooth_listener
{
    pfn_on_bluetooth_event_t onEvent;                        /**< 事件处理函数 */
    void *ctx;                                                /**< 监听器的上下文环境 */

    // 以下属性为私有,用户无需关注
    struct rt_list_node node;                                /**< 链表节点,用来链接所有的监听器链表 */
} st_bluetooth_listener_t, *pst_bluetooth_listener_t;
PRIVATE void BTNotifyListners(pst_bluetooth_event_t event)
{
    struct rt_list_node *node;
    pst_bluetooth_listener_t listener;

    BTLock();
    
    node = s_bluetoothPrivInfo.listenersHeader.next;
    while (node != &s_bluetoothPrivInfo.listenersHeader)
    {
        listener = rt_list_entry(node, st_bluetooth_listener_t, node);
        
        if (BF_NULL != listener->onEvent)
            listener->onEvent(listener->ctx, event);
        
        node = node->next;
    }

    BTUnlock();
}
bf_int_t BT_AddListener(pst_bluetooth_listener_t listener)
{
    PureReturnValIfFail(BF_NULL != listener, -1);
    
    BTLock();

    rt_list_insert_before(&s_bluetoothPrivInfo.listenersHeader, &listener->node);

    BTUnlock();
    
    return 0;
}

void BT_RemoveListener(pst_bluetooth_listener_t listener)
{
    PureReturnIfFail(BF_NULL != listener);
    
    BTLock();

    rt_list_remove(&listener->node);

    BTUnlock();
}

你可能感兴趣的:(c)