do {} while (0) зачем?

Do you have a question? Post it now! No Registration Necessary

Threaded View
Приветствую всех, коллеги!

  Задумали сделать одну разаработку на блекфине, с uCLinux на борту. Сам я  
с Линуксом не сильно знаком (на работе поставил debian на роутер, на нем и  
тренируюсь), поэтому есть пара вопросов:

1) Кому не лень иногда мылом или аськой отвечать на глупые вопросы про  
заточке uCLinux под мое железо, сборку инструментов и т.д.?
2) В исходниках Линукса встречается такая конструкция:
#define    SOME_THING        \
    do {                \
        func(arg1,arg2);    \
    } while (0)

что-то я никак не догоню, зачем функцию "оборачивать" в do {} while?

  С уважением,
   Сергей Борщ

--
Отправлено через сервер Форумы@mail.ru - http://talk.mail.ru

Re: do {} while (0) зачем?
Hello Sergey.

07 Oct 04 10:44, you wrote to all:

 SB> 1) Кому не лень иногда мылом или аськой отвечать на глупые вопросы про
 SB> заточке uCLinux под мое железо, сборку инструментов и т.д.?

Hаверное, лучше здесь, пока не выходит за рамки топика.

 SB> 2) В
 SB> исходниках Линукса встречается такая конструкция:
 SB> #define  SOME_THING \
 SB> do {                \
 SB> func(arg1,arg2);    \
 SB> } while (0)

 SB> что-то я никак не догоню, зачем функцию "оборачивать" в do {} while?

Где-то я встречал объяснение, счас не помню. Что-то связано с использованием
макроса в выражениях. Такой макрос всегда выглядит как один оператор. Hе
обращай внимания.

Alexey


Re: do {} while (0) зачем?
Привет Sergey!

07 Oct 04 11:44, Sergey A. Borshch писал All:

 SB> 1) Кому не лень иногда мылом или аськой отвечать на глупые вопросы про
 SB> заточке uCLinux под мое железо, сборку инструментов и т.д.?

    А можно не мылом? Я тоже как-то хотел его применить, мне было бы интересно
послушать. По поводу инструментов типа gcc и binutils могу лишь сказать, что с
этим (в отличие от uClinux) никаких проблем у меня никогда не было. Просто
делаешь все по инструкции - и все получается.

 SB>  2) В
 SB> исходниках Линукса встречается такая конструкция: #define
 SB> SOME_THING
 SB> \   do {                \       func(arg1,arg2);    \   } while (0)

 SB> что-то я никак не догоню, зачем функцию "оборачивать" в do {} while?

    Таким образом обычно в языке C оборачивают не функцию, а блок операторов
({}). Дело в том, что после блока операторов в языке C не ставится ";". В
результате если ты определишь такой макрос:

#define SMTHNG(x) \
    {
        f1((x) + 5);
        f2((x) - 10);
    }

    то тебе придется всегда помнить, что SMTHNG() - это не функция, а макрос, и
ставить после него ";" не надо, иначе это будет пустой оператор. А вот если
этот блок обернуть в do...while(0), то с точки зрения синтаксиса он уже будет
неотличим от вызова функции, что гораздо удобнее - не надо забивать себе голову
деталями, а потом искать, почему что-то не работает.

Всего наилучшего,                                 [Team PCAD 2000]
Алексей М.
... Западно-уральское региональное общество добровольных учредителей.

Re: do {} while (0) зачем?
Алексей, приветствую!
Quoted text here. Click to load it
У меня binutils не собрались - внутренняя ошибка в bison. Debian woodo под  
VMware. Попытка обновить его (bison) из unstable закончилась крахом  
системы. Восстанавливаю. Как соберу - пойдут более детальные вопросы.
Quoted text here. Click to load it
Мне обычно не везет :-)

Quoted text here. Click to load it
Понял. Видимо раньше там было несколько вызовов функций, но в процессе  
доработок осталась одна. Если бы их было больше одной, ответ был бы  
очевиден. Но решение красивое. Беру на заметку.

  С уважением,
   Сергей Борщ

--
Отправлено через сервер Форумы@mail.ru - http://talk.mail.ru

Re: do {} while (0) зачем?
7-Oct-04 17:08 Sergey A. Borshch wrote to Alex Mogilnikov:

SB> Но решение красивое. Беру на заметку.

Кроме устранения проблем с
 if( cond)
     SOME_FUNC;  //  { };  после разворачивания макроса
 else {
 }

это дело небезинтересно в таком виде

  ...
  do{ // естественно, коментарий что это не цикл
    ...

    if(error1)
      break;
    ...
    ...
    ...
    if(errorN)
      break;
    ...
  }while(0)

вместо
  ...
  if(!error1) {
     ...
          ...
               ...
                  if(errorN) {
                     ...
                  }
               }
          .
     .
  }

чтобы и не выехать очень далеко вправо, и не делать отдельную функцию
с if(errorK) return; в тех случаях, когда этой функции пришлось бы
передавать по ссылке [почти] все локальные переменные текущей функции.

Но я в таком виде while(0) применял может пару раз, очень уж непривычно
для себя самого выглядит. А были бы в С локальные функции, так и вообще
это не нужно было бы.

wbr,
--
/* Oleksandr Redchuk, Brovary, Ukraine */
/* real '\x40' real '\x2E' kiev '\x2E' ua     */


Re: do {} while (0) зачем?
Hello, Alex!
You wrote to Sergey A. Borshch on Thu, 07 Oct 2004 14:19:48 +0400:

 SB>> что-то я никак не догоню, зачем функцию "оборачивать" в do {}
 SB>> while?

 AM>     Таким образом обычно в языке C оборачивают не функцию, а блок
 AM> операторов ({}). Дело в том, что после блока операторов в языке C не
 AM> ставится ";".

    [...]
    Не только. Таким образом ещё реализуют "блок finally" :-)). Если нужно в
нескольких местах прерывать выполнение вложенного блока, то это можно
реализовать через goto, через развесистый if, либо через указанную
конструкцию:
(1)
    /* */
    if (a) goto label;
    /* */
    if (b) goto label;
    /* */
    if (c) goto label;
    /* */
    label:
(2)
    /* */
    if (!a)
        {
        /* */
        if (!b)
            {
            /* */
            if (!c)
                {
                /* */
                }
            }
        }
/*     label: */
(3)
    do
        {
        /* */
        if (a) break;
        /* */
        if (b) break;
        /* */
        if (c) break;
        /* */
        } while (0);
/*     label: */

    Кроме того, такая конструкция предоставляет некоторые удобства при
использовании отладчика - если "на метке" стоит return, то пр  необходимости
можно стать именно на него, а не искать все возвраты.
    Как по мне - это всё сомнительные преимущества (я имею в виду
перечисленные мной).

Alexander,Derazhne@adic,kiev,ua (replace commas with dots)
Alexander Derazhne



Re: do {} while (0) зачем?
Привет Alexander!

08 Oct 04 17:27, Alexander Derazhne писал Alex Mogilnikov:

 AD>     Hе только. Таким образом ещё реализуют "блок finally" :-)).

    А, да. Я так делал пару раз. Hо, конечно, не в виде макроса. :)

 AD>     Кроме того, такая конструкция предоставляет некоторые удобства при
 AD> использовании отладчика - если "на метке" стоит return, то пр
 AD> необходимости можно стать именно на него, а не искать все возвраты.
 AD>     Как по мне - это всё сомнительные преимущества (я имею в виду
 AD> перечисленные мной).

    Хорошее преимущество - я не люблю нагромождения вложенных if(). По break
гораздо понятнее куда идти.

Всего наилучшего,                                 [Team PCAD 2000]
Алексей М.
... Крыскас. Потому что крыса вам доверяет.

Site Timeline