|
|
  |
printf(), putchar(), fopen(), fclose(), fprintf() и т.д., суть реализации все этого для embedded? |
|
|
|
Aug 8 2009, 21:59
|
Местный
  
Группа: Участник
Сообщений: 328
Регистрация: 23-05-08
Пользователь №: 37 760

|
Запутался в конец ))). 1) Функции ввода-вывода, работающие со стандартными потоками ввода-вывода( printf, putchar и т.д.) - как они используются для embedded-приложений? Насколько понимаю, поток ввода, например, - это просто буфер, область памяти, обслуживаемая как FIFO? И в случае "Hello, World!" для Windows стандартные потоки ввода-вывода - это буферы, созданные операционной системой, а их размеры и указатели передаются приложению (моему "Helo, World!"). Значит в случае программы для микроконтроллера можно сделать свой поток - выделить область в ОЗУ (буфер), сделать указатели записи-чтения, определить размер буфера и тогда, скажем printf будет писать данные в этот буфер? И потом из этого буфера, скажем, передавать в UART? Я правильно понимаю? Или нет? Как все это правильно делается? У Т.Мартина в книге есть мелкий пример по использованию STDIO, где пишется своя функция putchar. После чего уже можно юзать printf(). Но у меня это вроде как сомнения вызывает... Без таких "доработок" нельзя? 2) Функции, работающие с файловыми потоками... Во-первых, что есть fopen для embedded? Во-вторых, структура FILE? В-третьих, функциями типа frintf, fwrite можно пользоваться для работы с собственными буферами? Если да, то как? Вообщем, как правильно использовать библиотеку STDIO для embedded-приложений? Собственно вот ))). Немного путано получилось... Если кто найдет время мне это все объяснить - буду очень признателен!
|
|
|
|
|
Aug 8 2009, 22:38
|

фанат дивана
     
Группа: Свой
Сообщений: 3 387
Регистрация: 9-08-07
Из: Уфа
Пользователь №: 29 684

|
Цитата(Student Pupkin @ Aug 9 2009, 03:59)  Значит в случае программы для микроконтроллера можно сделать свой поток - выделить область в ОЗУ (буфер), сделать указатели записи-чтения, определить размер буфера и тогда, скажем printf будет писать данные в этот буфер? Если в буфер, то ничего не надо определять, надо просто использовать sprintf()  Оно как раз для этого. Цитата Вообщем, как правильно использовать библиотеку STDIO для embedded-приложений? Если речь о gcc, то надо написать заглушки (stubs). Вот научно-популярное объяснение, что это такое, вот документация. А в аттаче
stf_syscalls_minimal.rar ( 1.34 килобайт )
Кол-во скачиваний: 211 - пример заглушек из какого-то примера от FreeRtos.
--------------------
Если бы я знал, что такое электричество...
|
|
|
|
|
Aug 8 2009, 23:53
|
Местный
  
Группа: Участник
Сообщений: 328
Регистрация: 23-05-08
Пользователь №: 37 760

|
Цитата(AHTOXA @ Aug 9 2009, 02:38)  Если в буфер, то ничего не надо определять, надо просто использовать sprintf()  Оно как раз для этого. Угумс )))). Да, есть такие sprintf(), sscanf. Про них понятно, суть их так сказать  . В них явно указывается указатель на строку, в которую пишем (вводим) или из которой читаем (выводим). Цитата(AHTOXA @ Aug 9 2009, 02:38)  Если речь о gcc, то надо написать заглушки (stubs). А вот тут я никак )))). Получается, что часть функций библиотеки stdio нормально использовать нельзя? Я имею ввиду обычное программу для микроконтролера, без использования оси (это называется StandAlone- приложение вроде бы?). А зачем же они тогда реализованы? И как они реализованы? Я в смысле, что в соотвествующей lib-е они есть, раз в хэдере прописаны? Что для них есть stdin, stdout? Как функция fopen работает? Не понимаю... Есть конечно сомнительная мысль, что эта часть функций реализована исключительно как ввод-вывод на консоль ИАРа под отладчиком (да кстати  , я тут с иаром вожусь, пытаюсь в хэдерах что-то на эту тему откопать... но пока не очень), возможно и работа с файлами (fopen, fwrite, fread и т.д.) тоже предполагается по житагу через ИАР (ну, по крайней мере знаю от товарищей, которые с TMS320 под CodeComposerStudio, что у них есть такое - по житагу из файла на ПЭВМ в ОЗУ процессора загрузить). А в целом картину я пока так и не понял  .
|
|
|
|
|
Aug 9 2009, 00:08
|
Гуру
     
Группа: Свой
Сообщений: 2 712
Регистрация: 28-11-05
Из: Беларусь, Витебск, Строителей 18-4-220
Пользователь №: 11 521

|
Стандартным выводом вроде как является UART. Но вы действительно можете переопределить п/п putchar() и сделать вывод туда, куда нужно. Ничего собственно заумного нет. Просто в своей программе объявляете и пишете данную процедуру. Я, например, писал данную процедуру для LCD. В результате у вас будет работать форматированный вывод. То же и с вводом. Например подключили матричную клавиатуру и обработали её.
Насколько это надо? Это уже другой вопрос. Ну например у вас достаточно толстый камень типа ARM7, либо даже старшие модели AVR. Выбрали вы их из соображений переферии. Например выбрали мега640, так как вам надо 80 ног для управления. А сама задача - проста как грабли. 64к флэши и 8к озу - достаточно выше крыши, чтобы не заморачиваться а писать используя printf. А саму задачу сначала отладить непосредственно на IBM со всеми причиндалами. Потом перенести на вашу мегу.
Кроме того, этоже не мешает совершенно. Ну например написали вы putchar, а printf не используете. Но при отладке в нескольких местах впёрли этот ваш printf и вывели HEX значение отлаживаемого параметра.
Могу сказать, что printf в урезанном виде работает даже на atmega8.
|
|
|
|
|
Aug 9 2009, 00:38
|

Нечётный пользователь.
     
Группа: Свой
Сообщений: 2 033
Регистрация: 26-05-05
Из: Бровари, Україна
Пользователь №: 5 417

|
Цитата(Student Pupkin @ Aug 9 2009, 02:53)  Получается, что часть функций библиотеки stdio нормально использовать нельзя? Я имею ввиду обычное программу для микроконтролера, без использования оси (это называется StandAlone- приложение вроде бы?). А зачем же они тогда реализованы? И как они реализованы? А как реализуете, так и будет :-) Цитата(Student Pupkin @ Aug 9 2009, 02:53)  Есть конечно сомнительная мысль, что эта часть функций реализована исключительно как ввод-вывод на консоль ИАРа под отладчиком (да кстати  Как уже говорилось, в простейшем случае переопределяется единственная функция putchar() и тогда printf лупит через неё туда, куда захотел программист. У avr-gcc функции fprintf/vfprintf принимают файловый объект, в котором записаны указатели на соответствующие этим объектам функции вывода и ввода символа, можно определить несколько совершенно разнородных "псевдофайлов" и работать с ними. Для сокращения кода имеются макросы, инициализирующие глобальные файловые переменные во время компиляции. Как-то так: http://electronix.ru/forum/index.php?showt...mp;#entry596833http://electronix.ru/forum/index.php?showt...mp;#entry463352Если очень хочется, можно написать свои fopen под свою систему, заполняющие структуру FILE, как в данных ранее линках в зависимости от переданного аргумента. Ну или как это сделано в NutOS (то, что там OS - несколько ортогонально к применённой системе "файлов", это и в "безосевом" приложении можно было бы сделать).
--------------------
Ну, я пошёл… Если что – звоните…
|
|
|
|
|
Aug 9 2009, 08:04
|

фанат дивана
     
Группа: Свой
Сообщений: 3 387
Регистрация: 9-08-07
Из: Уфа
Пользователь №: 29 684

|
Цитата(Student Pupkin @ Aug 9 2009, 05:53)  А вот тут я никак )))). Получается, что часть функций библиотеки stdio нормально использовать нельзя? Я имею ввиду обычное программу для микроконтролера, без использования оси (это называется StandAlone- приложение вроде бы?). Ух, сколько вопросов! Отвечаю по порядку Использовать без оси можно, надо только написать несколько недостающих функций. Цитата А зачем же они тогда реализованы? И как они реализованы? Я в смысле, что в соотвествующей lib-е они есть, раз в хэдере прописаны? Что для них есть stdin, stdout? Как функция fopen работает? Не понимаю... Реализованы они для соответствия стандарту. И для удобства программста  В либе они есть. Как реализованы - попробую рассказать на примере printf. Функция printf внутри библиотеки делает всю работу по преобразованию строки формата и аргументов в нужную для вывода последовательность символов, и потом вызывает putchar() для этих символов в нужном порядке. Функция putchar() обычно не реализована в библиотеке, потому что библиотека не знает, куда пользователь пожелает выводить символы. stdin и stdout - обычные файлы, просто их имена предопределены, и они открываются в стартапе. Пример работы fopen() был по первой моей ссылке. Цитата (да кстати  , я тут с иаром вожусь, пытаюсь в хэдерах что-то на эту тему откопать... но пока не очень) Насчёт ИАР не знаю, скорее всего там попроще, достаточно определить putchar/getchar. И копать надо не в хидерах, а в документации
--------------------
Если бы я знал, что такое электричество...
|
|
|
|
|
Aug 9 2009, 13:28
|
Местный
  
Группа: Участник
Сообщений: 328
Регистрация: 23-05-08
Пользователь №: 37 760

|
Цитата(AHTOXA @ Aug 9 2009, 12:04)  Насчёт ИАР не знаю, скорее всего там попроще, достаточно определить putchar/getchar. И копать надо не в хидерах, а в документации  Да, действительно искал не там  . У Кернигана и Ритчи в главе "Интерфейс с ситемой UNIX" есть раздел "Нижний уровень ввода-вывода (read и write)"... Надо было до этого места дочитать  . В ИАРе нашел, где про это написано  . Пишут, что в конечном счете для использования функций ввода-вывода необходимо написать свои версии функций __read и __write. Тоже самое касается функций для работы с файлами - необходимо написать свои версии для нескольких низкоуровневых функций (__open, __close и др.). Причем установкой опций линкера можно включить варианты функций ввода-вывода, которые будут работать по житагу с хостом - выводить, открывать-закрывать файл и т.д. Всем спасибо  . Пойду учиться дальше  .
|
|
|
|
|
  |
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|