当前位置: 技术问答>linux和unix
[请教]有关原码的
来源: 互联网 发布时间:2015-06-25
本文导语: #define SET_LINKS(p) do { (p)->next_task = &init_task; (p)->prev_task = init_task.prev_task; init_task.prev_task->next_task = (p); init_task.prev_task = (p); (p)->p_ysptr = NULL; if (((p)->p_osptr = (p)->p_pptr->p_cptr) != NULL) (p)->p_osptr->p_...
#define SET_LINKS(p) do {
(p)->next_task = &init_task;
(p)->prev_task = init_task.prev_task;
init_task.prev_task->next_task = (p);
init_task.prev_task = (p);
(p)->p_ysptr = NULL;
if (((p)->p_osptr = (p)->p_pptr->p_cptr) != NULL)
(p)->p_osptr->p_ysptr = p;
(p)->p_pptr->p_cptr = p;
} while (0)
看到上面一段原代码,始终没明白这个宏定义中的do...while(0)是怎么回事,while中的判断条件被赋予了“0”,那么这个循环体不论在何种情况下都只会执行一次,如果真是这样的话,直接写出循环体中的代码就可以了吧,为什么还偏偏要循环呢,我觉得有点不可理解。但是另我费解的是,似乎内核中有很多宏定义都使用了这样的语句“do...while(0)”,不知道这样子的代码到底有什么奥妙,请高手赐教。
(p)->next_task = &init_task;
(p)->prev_task = init_task.prev_task;
init_task.prev_task->next_task = (p);
init_task.prev_task = (p);
(p)->p_ysptr = NULL;
if (((p)->p_osptr = (p)->p_pptr->p_cptr) != NULL)
(p)->p_osptr->p_ysptr = p;
(p)->p_pptr->p_cptr = p;
} while (0)
看到上面一段原代码,始终没明白这个宏定义中的do...while(0)是怎么回事,while中的判断条件被赋予了“0”,那么这个循环体不论在何种情况下都只会执行一次,如果真是这样的话,直接写出循环体中的代码就可以了吧,为什么还偏偏要循环呢,我觉得有点不可理解。但是另我费解的是,似乎内核中有很多宏定义都使用了这样的语句“do...while(0)”,不知道这样子的代码到底有什么奥妙,请高手赐教。
|
假如上述宏不是这样定义,而是:
#define SET_LINKS(p) {......}
看起来应该完全一样,但是如果按如下方法调用:
if (...)
SET_LINKS(ptr);
else {...}
则连编译都通不过,不信,你可以试试。如果将SET_LINKS(p)定义成do{...}while(0)方式,则没有问题。
#define SET_LINKS(p) {......}
看起来应该完全一样,但是如果按如下方法调用:
if (...)
SET_LINKS(ptr);
else {...}
则连编译都通不过,不信,你可以试试。如果将SET_LINKS(p)定义成do{...}while(0)方式,则没有问题。
|
那样会有多余的分号