打印
[ZLG-ARM]

(uint32)(((DataQueue *)0) 什么意思

[复制链接]
1981|9
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
myoiqq|  楼主 | 2008-2-26 18:05 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
在数据队列创建函数
        uint8 QueueCreate(void *Buf,
                          uint32 SizeOfBuf,
                          uint8 (* ReadEmpty)(),
                          uint8 (* WriteFull)()
                          )
{
    DataQueue *Queue;
    
    if (Buf != NULL && SizeOfBuf >= (sizeof(DataQueue)))        /* 判断参数是否有效 */
    {
        Queue = (DataQueue *)Buf;

        OS_ENTER_CRITICAL();
                                                                /* 初始化结构体数据 */
        Queue->MaxData = (SizeOfBuf - (uint32)(((DataQueue *)0)->Buf)) / 
                         sizeof(QUEUE_DATA_TYPE);
        Queue->End = Queue->Buf + Queue->MaxData;               /* 计算数据缓冲的结束地址 */
        Queue->Out = Queue->Buf;
        Queue->In = Queue->Buf;
        Queue->NData = 0;
        Queue->ReadEmpty = ReadEmpty;
        Queue->WriteFull = WriteFull;

        OS_EXIT_CRITICAL();

        return QUEUE_OK;
    }
    else
    {
        return NOT_OK;
    }
}
中计算最大数据数目然后给了Queue->MaxData,试问一下(uint32)(((DataQueue *)0)->Buf什么意思呢?

相关帖子

沙发
dld2| | 2008-2-26 18:32 | 只看该作者

有意思

实际上就是DataQueue结构中buf这个成员变量在结构中的相对位置。

把0强制转换为DataQueue类型的指针,就是为了计算这个偏移值。

使用特权

评论回复
板凳
myoiqq|  楼主 | 2008-2-26 19:25 | 只看该作者

补充

typedef struct {
    QUEUE_DATA_TYPE     *Out;                   /* 指向数据输出位置         */
    QUEUE_DATA_TYPE     *In;                    /* 指向数据输入位置         */
    QUEUE_DATA_TYPE     *End;                   /* 指向Buf的结束位置        */
    uint16              NData;                  /* 队列中数据个数           */
    uint16              MaxData;                /* 队列中允许存储的数据个数 */
    
    uint8               (* ReadEmpty)();        /* 读空处理函数             */
    uint8               (* WriteFull)();        /* 写满处理函数             */
    QUEUE_DATA_TYPE     Buf[1];                 /* 存储数据的空间           */
} DataQueue;

使用特权

评论回复
地板
myoiqq|  楼主 | 2008-2-26 19:41 | 只看该作者

dld2 说法不能理解

我觉得dld2 说法还是不能理解,如果是得到Buf的首地址,那么这个首地址是如何计算数据的长度呢?计算公式?

使用特权

评论回复
5
dld2| | 2008-2-26 19:52 | 只看该作者

这样说:

Queue->MaxData = (SizeOfBuf - (uint32)(((DataQueue *)0)->Buf)) / 
                         sizeof(QUEUE_DATA_TYPE);
//队列中的最大数据单元数量 = (总缓冲区长度 - (从Out到WriteFull所占的空间的大小))/数据单元的大小

使用特权

评论回复
6
myoiqq|  楼主 | 2008-2-26 19:58 | 只看该作者

讨论

(总缓冲区长度 - (从Out到WriteFull所占的空间的大小))/数据单元的大小
这样得到的应该是从开始到Out的数据单元个数。

使用特权

评论回复
7
dld2| | 2008-2-26 20:04 | 只看该作者

对不上点,呵呵

使用特权

评论回复
8
myoiqq|  楼主 | 2008-2-26 20:10 | 只看该作者

无语

其实完全可以有许多让人更加容易理解的做法。不知道为什么非要这么写

使用特权

评论回复
9
dld2| | 2008-2-26 20:23 | 只看该作者

其实蛮精妙的

原因之一:QUEUE_DATA_TYPE是个宏,可以定义为int、char、或者一个结构。

就是说:这是一个存储空间外部分配、总长度可变、数据单元大小可配置的通用队列。
并且提供了读空和写满时的回调函数。

不知道这段代码是哪里来的。

使用特权

评论回复
10
wlsui| | 2008-2-27 00:04 | 只看该作者

RE:

这段代码是ZLG的数据队列中间件中的代码,这样写的好处是更灵活,不受所声明类型的具体实现限制

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

12

主题

38

帖子

0

粉丝