megajohn 5 24 сентября, 2013 Опубликовано 24 сентября, 2013 · Жалоба первоначально передача была сделана по одному байту. но после написания драйвера для отправки по SSP с использованием FIFO решил так же переписать уартовский, но не тут то было. нет привычных битов TFE Transmit FIFO Empty, TNF Transmit FIFO Not Full хотя в доке написано 16 byte Receive and Transmit FIFOs у меня сложилось мнение что из указанных 16 остается 14 байт на RX и лишь два байта на TX. Так ? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
GetSmart 0 24 сентября, 2013 Опубликовано 24 сентября, 2013 · Жалоба Два независимых буфера для RX и TX. К примеру, в LPC1768 кажется нет индикатора заполненности TX буфера. Как и в LPC21xx, LPC111x. Так что забиваются по полному освобождению сразу 16 байт. В RX прерывании, если стоит уровень срабатывания 14, то можно вычитывать из RBR сразу 14 раз подряд, анализируя младший бит LSR. Пример обработчика void UART0_IRQHandler() { switch(U0IIR & 0x0f) { uInt lsr; default: U0LSR; U0RBR; break; case 0x02: //THRE interrupt proc_tx(&uart0); break; case 0x0C: //timeout case 0x06: //Rx line status error case 0x04: //Receive data available while ((lsr = U0LSR) & 0x01) proc_rx(&uart0, U0RBR, lsr & 0x9e); break; } NVIC_ClearPendingIRQ(UART_IRQn); } //uart0 - структура с данными Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Golikov 0 24 сентября, 2013 Опубликовано 24 сентября, 2013 · Жалоба а разве не появляется флаг буфер передатчика занят когда все 16 байт заняты? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
jcxz 228 24 сентября, 2013 Опубликовано 24 сентября, 2013 · Жалоба а разве не появляется флаг буфер передатчика занят когда все 16 байт заняты? Нет. Там эмуляция стандартного, не самого удачного 16550. Флаг "буфер пуст" снимается при записи хотя-бы одного байта в TX-fifo. Так что при обнаружении этого флага, писать надо сразу <= 16 байт. С RX не так печально. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Terminator 0 26 сентября, 2013 Опубликовано 26 сентября, 2013 · Жалоба Мне удалось нормально запустить uart TX на lpc1768 только с использованием DMA. Прерывания от самого uart весьма странно работают. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
jcxz 228 26 сентября, 2013 Опубликовано 26 сентября, 2013 · Жалоба А что там странного? Вполне соответствуют описанию в UM. И таких контроллеров полно во многих других процессорах других фирм - одна из самой распространённой периферии ;) У меня в проекте все 4 UART на lpc1758 работают в параллель с FIFO и по прерываниям - никаких проблем. А на LPC1778 - все 5. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Terminator 0 27 сентября, 2013 Опубликовано 27 сентября, 2013 (изменено) · Жалоба беда в том что прерывание TX_EMPTY может возникнуть только после передачи. Если его просто разрешить, когда никакой передачи не идёт, ничего не произойдёт. В других контроллерах (с которыми я имел дело) при разрешении такого прерывания немедленно вызывался обработчик. Такое поведение очень сильно упрощает "драйвер" работы с uart-ом. Изменено 27 сентября, 2013 пользователем Terminator Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Golikov 0 27 сентября, 2013 Опубликовано 27 сентября, 2013 · Жалоба что значит вызывается обработчик при разрешении? Обработчик должен вызывать при возникновении прерывания а не просто при его разрешении... Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ig_z 0 27 сентября, 2013 Опубликовано 27 сентября, 2013 · Жалоба что значит вызывается обработчик при разрешении? Обработчик должен вызывать при возникновении прерывания а не просто при его разрешении... При возникновении прерывания "должен" ставиться флаг запроса на прерывание и ничего более. При разрешении прерывания и установленном флаге запроса контроллер прерывания запускает обработчик. Что курили голландские девелоперы, когда дизайнили уарт известно только им и богу. По факту код передачи по уарту для филипков должен быть продублирован в обработчике прерывания от уарта и в том месте кода, где нужно начать передачу. Для "нормальных" уарт архитектур достаточно разрешить прерывание "передатчик пуст" Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Golikov 0 27 сентября, 2013 Опубликовано 27 сентября, 2013 · Жалоба чего то я не понимаю видать.... у меня это было так. функция послать данные: если передатчик и доп буфер пусты пихает в передатчик 16 байт данных. Если их меньше и ладно, если их больше пихает 16 остальные кладет в буфер программный. если доп буфер был не пуст, кладет данные в него. прерывание уарт пуст - если буфер программный пуст и ладно, если нет, то берет данные из него и пихает в передатчик. я так понимаю что проблема ваша в том что при пустом буфере надо данные в него положить, а не в программный буфер... ну так это добавление одного ифа в функции отправки, зато момент отправки четко обозначен, можно чип селект какой - либо опустить... вообщем никакой проблемы я не вижу если честно, все мне кажется логично... А вот что делать с прерывание буфер пуст если оно возникает всегда когда буфер пуст для меня как раз вопрос. Ведь большую часть времени если обмена нет, он как раз и пуст, вы прерывание что-ли запрещаете, а когда данные кладете разрешаете? Не уверен, что это прям мего логично... Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ig_z 0 27 сентября, 2013 Опубликовано 27 сентября, 2013 · Жалоба вообщем никакой проблемы я не вижу если честно, все мне кажется логично... А вот что делать с прерывание буфер пуст если оно возникает всегда когда буфер пуст для меня как раз вопрос. Ведь большую часть времени если обмена нет, он как раз и пуст, вы прерывание что-ли запрещаете, а когда данные кладете разрешаете? Не уверен, что это прям мего логично... Если вопрос ко мне, то в общем виде картина передачи данных выглядит так: - аппликейшн никогда не работает с уарт прямо. Только через кольцевой буфер. - после получения данных буфер проверяет разрешены ли прерывания на передачу и разрешает их, если запрещены. - обработчик прерывания заполняет выходной регистр (или выходное фифо) данными. Если данные закончились - запрещает преравания на передачу Прерывания разрешаются когда есть данные и запрещаются когда из нет. Просто , логично, компактно и надежно Ну и вы конечно правы, с уарт на лпс нет никаких проблем, одно мелкое неудобство. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Golikov 0 27 сентября, 2013 Опубликовано 27 сентября, 2013 · Жалоба вы проверяете разрешено ли прерывание, и разрешаете их если запрещены. я проверяю пустой ли буфер обмена вы пихаете данные в кольцевой буфер а оттуда в фифо уарта я в первом случае пихаю их сразу в фифо, на 1 копирование меньше разрешать и запрещать прерывания - просто логично, но не факт что надежно, мало ли кто еще в программе решит их запретить и почему? идиологии разные и обе имеют как плюсы так и минусы. И если вы всегда делали так, не значит что по другому не удобно. Главное что это все описано в мануале, а значит проблем нет. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
jcxz 228 27 сентября, 2013 Опубликовано 27 сентября, 2013 · Жалоба Да, конечно, 16550 уже давно морально устарел и можно сделать гораздо более удобный и современный интерфейс для UART (примеры есть). Но NXP решили для UART реализовать стандартный 16550 (с доп. фичами) и у этого подхода есть и серьёзный '+': UART - это единственная периферия, драйвера для которой я переношу между разными контроллерами практически без изменений, а это серьёзный '+' когда приходится одновременно работать с разными контроллерами. И реализовали они его грамотно - без багов. Что курили голландские девелоперы, когда дизайнили уарт известно только им и богу. По факту код передачи по уарту для филипков должен быть продублирован в обработчике прерывания от уарта и в том месте кода, где нужно начать передачу.В си есть такая чудесная вещь как функция(). Попробуйте - вам понравится ;) Для "нормальных" уарт архитектур достаточно разрешить прерывание "передатчик пуст"Это уж не в тех-ли нормальных (типа STM), где забыли добавить FIFO в UART? ;) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ig_z 0 27 сентября, 2013 Опубликовано 27 сентября, 2013 · Жалоба Это уж не в тех-ли нормальных (типа STM), где забыли добавить FIFO в UART? ;) s3c4530 догадливый вы наш Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Terminator 0 28 сентября, 2013 Опубликовано 28 сентября, 2013 · Жалоба это всё конечно красиво, но попробуйте сделать вывод в отладочный порт из разных задач. Останавливать задачу ради вывода отладки нельзя, что влезло в буфер, то влезло. Заводить отдельную задачу для слежения за заполненостью буфера, очень не хочется. Запрещать прерывания перед каждым обращением в uart тоже (тут я конечно несколько лукавлю, т.к. при складывании в буфер прерывания всё равно запрещаются). Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться