<HTML><BODY>Привет всем, я хотел написать тебе, Боря, еще вчера. Г.А все верно сказал, что ты не до конца<br>понимаешь, для чего нужны эти ф-ии/макросы в Си. И как хранятся аргументы.<br><br>printf(char *fmt, void *args, int nargs)<br><br><span style="font-size: 12px;">в твоем предложенном варианте аргументы уже хранятся в подготовленном массиве, и в ф-ию<br>передаются только </span>указатель на массив, его размерность + конечно же сама форматная строка, так<br>вот получается на стеке в итоге находится 3 аргумента.<br><br>Когда же мы говорим про оригинальную версию printf, то ВСЕ аргументы хранятся в регистрах и/или в<br>стеке (в зависимости как и сказал Г.А. от ABI), сколько ты их передашь это не имеет значение. И если<br>посмотреть на реализацию самой printf, то она полагается на форматную строку, и данные извлеченные<br>из стека/регистров с помощью va_arg интерпретируются согласно спецификации строки, то есть количество<br>аргументов заведомо не передается.<br><br>То есть еще раз:<br><br>1. все аргументы живут в стеке/регистрах (нет промежуточного хранилища, типа массива);<br><br>2. количество аргументов не передается;<br><br>3. форматная строка это то на что полагаются при извлечении аргументов (если строка косячная и не соотвествует<br>извлеченным данным всего скорее программа скоро завалится, при первом обращении к данным).<br><br>Если ты хочешь избавится от количества аргументов в своей реализации и от промежуточного массива, почему<br>бы тебе не создавать конечную строку динамически, извлекая одновременно операцией pop свои значения<br>и консультируясь со своей форматной строкой. Посмотри для примера<br><br><a href="http://wiki.syktsu.ru/websvn/filedetails.php?repname=litepac&path=%2Fvmlibcall%2Fio.c" data-mce-href="http://wiki.syktsu.ru/websvn/filedetails.php?repname=litepac&path=%2Fvmlibcall%2Fio.c">http://wiki.syktsu.ru/websvn/filedetails.php?repname=litepac&path=%2Fvmlibcall%2Fio.c<br><br></a>Удачи.<br><br><br>Вторник, 16 апреля 2013, 10:43 +04:00 от Борис Липин <lonely.ruyk@mail.ru>:<br>
<blockquote style="border-left:1px solid #0857A6; margin:10px; padding:0 0 0 10px;" class="mailru-blockquote">
        <div id="">
        
        
        
        
        
        
        
        
<div class="js-helper js-readmsg-msg">
        <style type="text/css"></style>
        <div id="style_13660946100000000169" class="mr_read__body">
                <base target="_self" href="https://e.mail.ru/cgi-bin/">
                
                        <div id="style_13660946100000000169_BODY">
<p>Я подумал что с такой интерфейс выглядит более стандартным и каноничным.<br>В конечном итоге ведь и printf(3) функции могли реализовать как то вроде:<br>printf(char *fmt, void *args, int nargs).<br>Спасибо за ответ, наверное я действительно немного не прав относительно интерфейса функций.:)<br><br>А вообще есть возможность сделать преобразование array -> va_list или запихать массив в функции с переменным количеством параметров *стандартными средствами* или эта ситуация - совсем не то для чего они используются и о таких вопросах не стоит задумываться?<br><br><br>Понедельник, 15 апреля 2013, 21:59 +04:00 от "Grigoriy A. Sitkarev" <sitkarev@komitex.ru>:<br>
</p><blockquote style="border-left:1px solid #0857A6;margin:10px;padding:0 0 0 10px;">
        <div id="">
        
        
        
        
        
        
        
        
<div>
        
        <div id="style_13660488090000000757">
                
                
                        <div id="style_13660488090000000757_BODY">Всем здоровья!<br>
<br>
lonely.ruyk wrote:<br>
> Небольшой вопрос по поводу va_list:<br>
> Сейчас интерфейс функции форматированного вывода выглядит так:<br>
> <br>
> int var_print_formatted(struct variable *fmt, struct variable **args,<br>
> int nargs);<br>
> <br>
> хотелось бы сделать чтобы она выглядела как то так<br>
> <br>
> int var_print_formatted(struct variable *fmt, va_list ap);<br>
> или так<br>
> int var_print_formatted(struct variable *fmt, ...);<br>
> <br>
<br>
Я думаю, что тебе не совсем понятно, откуда вообще взялся va_list и <br>
сопровождающие его макросы va_start(), va_end(), va_copy() и va_arg(). <br>
Они появились для того, чтобы обеспечить переносимость Си функций, <br>
принимающих переменное количество аргументов, с одной машины на другую, <br>
без привязок к особенностям ABI.<br>
<br>
В твоём случае мы имеем дело с интерпретатором, где сами переменные и <br>
аргументы при вызове функций хранятся некоторым образом в его состоянии <br>
времени выполнения. Сам интерпретатор может полностью контроллировать <br>
сколько значений было передано функции при вызове, поэтому необходимости <br>
в va_list для передачи аргументов никакой нет.<br>
<br>
Чем плох нынешний вариант с передачей аргументов в массиве? В конце <br>
концов, кто запрещает сделать структуру<br>
<br>
struct arg_list {<br>
        const struct variable **item;<br>
        int        nitems;<br>
        int        nalloc;<br>
};<br>
<br>
int var_print_formatted(const struct variable *fmt, const struct <br>
arg_list *args);<br>
<br>
<br>
--<br>
Г.А.<br>
<br>
_______________________________________________<br>
Lab mailing list<br>
<a target="_blank">Lab@amplab.syktsu.ru</a><br>
<a href="http://amplab.syktsu.ru/cgi-bin/mailman/listinfo/lab" target="_blank">http://amplab.syktsu.ru/cgi-bin/mailman/listinfo/lab</a></div>
                        
                
                
        </div>
        
</div>
</div>
</blockquote><p>
<br></p>
</div>
                        <div>_______________________________________________<br>
Lab mailing list<br>
<a href="sentmsg?compose&To=Lab@amplab.syktsu.ru">Lab@amplab.syktsu.ru</a><br>
<a href="http://amplab.syktsu.ru/cgi-bin/mailman/listinfo/lab" target="_blank">http://amplab.syktsu.ru/cgi-bin/mailman/listinfo/lab</a></div>
                
                <base target="_self" href="https://e.mail.ru/cgi-bin/">
        </div>
        
</div>
</div>
</blockquote>
<br></BODY></HTML>