реклама на сайте
подробности

 
 
 
Reply to this topicStart new topic
> printf и несколько UART
dimka76
сообщение Oct 25 2007, 10:45
Сообщение #1


developer
****

Группа: Свой
Сообщений: 902
Регистрация: 12-04-06
Из: Казань
Пользователь №: 16 032



Когда изпользуетс вывод через один UART все понятно, пишем свою putchar.
А если требуется работать с несколькими UART и еще SPI, TWI и во всех случаях использовать printf, как быть в этом случае?


--------------------
Все может быть и быть все может, и лишь того не может быть-чего уж точно быть не может, хотя..и это может быть.
Go to the top of the page
 
+Quote Post
Палыч
сообщение Oct 25 2007, 10:52
Сообщение #2


Гуру
******

Группа: Свой
Сообщений: 2 399
Регистрация: 10-05-06
Из: г. Новочеркасск
Пользователь №: 16 954



Конечно же написать свои функции, или одну универсальную, по функциональности такую же, как и printf.
Go to the top of the page
 
+Quote Post
prottoss
сообщение Oct 25 2007, 10:58
Сообщение #3


Гуру
******

Группа: Свой
Сообщений: 2 720
Регистрация: 24-03-05
Пользователь №: 3 659



Хм... smile.gif А зачем использовать printf для второго(третьего, четвертого...) USART и тем более для TWI и SPI???. Обычно, данная функция используется для отладки. Для работы лучше написать что нибудь свое, менее тяжеловесное.


--------------------
Go to the top of the page
 
+Quote Post
defunct
сообщение Oct 25 2007, 11:01
Сообщение #4


кекс
******

Группа: Свой
Сообщений: 3 825
Регистрация: 17-12-05
Из: Киев
Пользователь №: 12 326



Цитата(dimka76 @ Oct 25 2007, 13:45) *
Когда изпользуетс вывод через один UART все понятно, пишем свою putchar.
А если требуется работать с несколькими UART и еще SPI, TWI и во всех случаях использовать printf, как быть в этом случае?

putchar можно сделать зависимым от какого-то глобального флага, e.g.
Код
U8 DevConOut = 0;

int putchar( int ch)
{
    switch( DevConOut )
    {
      case DEV_UART0:
          ....
          break;
      case DEV_UART1:
          ....
          break;
      case DEV_SPI:
          ...
          break;
      default:
          ...
          break;
    }
}
printf заменить макросом:
Код
#define my_printf( conout,  x ) do \
    {\
        DevConOut = (conout);\
        printf (x);\
    } while (0)

который использовать например так:
Код
my_printf( DEV_UART1, ("hello"));
my_printf( DEV_SPI, ("hello"));
Обрамлять второй параметр my_printf в скобочки - обязательно!
Go to the top of the page
 
+Quote Post
prottoss
сообщение Oct 25 2007, 11:03
Сообщение #5


Гуру
******

Группа: Свой
Сообщений: 2 720
Регистрация: 24-03-05
Пользователь №: 3 659



Ну, а уж если все таки приспичило, можно в putchar ввести глобальный флаг и переключать его в функции, которая вызывает printf, и которая знает, в какой интерфейс будет идти сообщение...
Код
char g_putcharMode = 0;
...
int putchar(int c)
{    
     switch(g_putcharMode)
     {
            case USART0_MSG:
            ...
            break;

            case USART1_MSG:
            ...
            break;

            case SPI_MSG:
            ...
            break;

             ...
     }

      return 0;
}


--------------------
Go to the top of the page
 
+Quote Post
Сергей Борщ
сообщение Oct 25 2007, 11:11
Сообщение #6


Гуру
******

Группа: Модераторы
Сообщений: 8 455
Регистрация: 15-05-06
Из: Рига, Латвия
Пользователь №: 17 095



Цитата(defunct @ Oct 25 2007, 14:01) *
putchar можно сделать зависимым от какого-то глобального флага, e.g.
Или использовать fprintf, но тогда придется подобным образом переписать не putchar, а какую-то другую функцию, в ИАР, например, это функция __write(). Ей номер устройства вывода передается как параметр, что позволяет использовать ее в многопоточных приложениях.


--------------------
На любой вопрос даю любой ответ
"Write code that is guaranteed to work, not code that doesn’t seem to break" (C++ FAQ)
Go to the top of the page
 
+Quote Post
Палыч
сообщение Oct 25 2007, 11:14
Сообщение #7


Гуру
******

Группа: Свой
Сообщений: 2 399
Регистрация: 10-05-06
Из: г. Новочеркасск
Пользователь №: 16 954



Цитата(prottoss @ Oct 25 2007, 15:03) *
Ну, а уж если все таки приспичило, можно в putchar ввести глобальный флаг и переключать его в функции, которая вызывает printf, и которая знает, в какой интерфейс будет идти сообщение...

Можно, конечно, и так, но, только вывод в UART, SPI, TWI нельзя будет осуществлять одновременно. Правда, мне не понятно зачем вывод с помощью printf автору вопроса потребовался во все эти устройства. Да, и вообще, printf - слишком тяжелая для микроконтроллеров функция (как правильно указал prottoss), без которой во многих случаях можно обойтись.
Go to the top of the page
 
+Quote Post
ReAl
сообщение Oct 25 2007, 11:16
Сообщение #8


Нечётный пользователь.
******

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



"компилятор по умолчанию"? wink.gif

А вот если avr-gcc, то можно создать любое количество описателей потока

Код
int some_putchar(char c, FILE *stream);

FILE some_stream = FDEV_SETUP_STREAM(some_putchar,  NULL, _FDEV_SETUP_WRITE);

и дальше пользоваться fprintf/fprintf_P/fputs/fputs_P/vfprintf_P ( &some_stream,
если при создании потока вторым параметром дать get-функцию, то и всем остальным стандартным.
Независимо и без передёргивания флагов.

А по поводу "printf только для отладки" - если в системе есть несколько текстовых потоков (текстовый протокол по UART, какой-нибудь термопринтер, ... и есть запас флеша/стека (а раз при отладке помещалось, значит есть) - то просто удобно пользоваться стандартными функциями везде.
Да и отладить многие куски форматирования/передачи можно через те же стандартные функции на персоналке.


--------------------
Ну, я пошёл… Если что – звоните…
Go to the top of the page
 
+Quote Post
defunct
сообщение Oct 25 2007, 11:22
Сообщение #9


кекс
******

Группа: Свой
Сообщений: 3 825
Регистрация: 17-12-05
Из: Киев
Пользователь №: 12 326



Цитата(Палыч @ Oct 25 2007, 14:14) *
Да, и вообще, printf - слишком тяжелая для микроконтроллеров функция (как правильно указал prottoss), без которой во многих случаях можно обойтись.

(imho)
Для m32 и выше - удобство printf перевешивает "тяжесть".
Для более мелких - да, выгоднее писать свои функции.
Go to the top of the page
 
+Quote Post
alexander55
сообщение Oct 25 2007, 11:40
Сообщение #10


Бывалый
*****

Группа: Свой
Сообщений: 1 584
Регистрация: 7-08-07
Пользователь №: 29 615



Цитата(Палыч @ Oct 25 2007, 15:14) *
Можно, конечно, и так, но, только вывод в UART, SPI, TWI нельзя будет осуществлять одновременно. Правда, мне не понятно зачем вывод с помощью printf автору вопроса потребовался во все эти устройства. Да, и вообще, printf - слишком тяжелая для микроконтроллеров функция (как правильно указал prottoss), без которой во многих случаях можно обойтись.

Мне кажется, функция printf используется:
1. Чаще всего для отладки. Терминал всегда один. Одновременно посылать никогда не надо. Иногда надо переключить UART (очень редко).
2. Внутри в самодельных пультов управления. Вобще не имеет отношения к поднятому вопросу. Удобнее использовать sprinf.
PS. Проблема носит теоретический характер. smile.gif
Go to the top of the page
 
+Quote Post
prottoss
сообщение Oct 25 2007, 11:48
Сообщение #11


Гуру
******

Группа: Свой
Сообщений: 2 720
Регистрация: 24-03-05
Пользователь №: 3 659



Цитата(alexander55 @ Oct 25 2007, 19:40) *
...Терминал всегда один...
По поводу того, что printf для отладки - согласен. А вот, что термнал всего один - нет. Терминалов может быть несколько. Один - для отладки, допустим на USART. Второй, к примеру на SPI - рабочий терминал устройства.

С первым работаем через printf, включая, допустим в макрос, который после отладки отключается.

Для второго пишем свой движок для эффективного вывода.


--------------------
Go to the top of the page
 
+Quote Post
dimka76
сообщение Oct 25 2007, 11:50
Сообщение #12


developer
****

Группа: Свой
Сообщений: 902
Регистрация: 12-04-06
Из: Казань
Пользователь №: 16 032



всем спасибо.
эта идея чисто абстрактная, на всякий случай так сказать.
defunct прав, при больших объемах FLASH, SRAM, удобство printf перевешивает "тяжесть". Да, и если быстродействия не требуется.
А идея с макросами от defunct мне понравилась больше всего.

Кстати компилятор IAR, хотя это наверное не принципиально, если подразумевается переносимость кода.


--------------------
Все может быть и быть все может, и лишь того не может быть-чего уж точно быть не может, хотя..и это может быть.
Go to the top of the page
 
+Quote Post

Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 18th July 2025 - 20:24
Рейтинг@Mail.ru


Страница сгенерированна за 0.01484 секунд с 7
ELECTRONIX ©2004-2016