Нестандартное использование UART в качестве генератора частоты

В общем-то, ничего особенного, нужно выдавать пачки меандра заданной частоты и в зависимости от требуемой интенсивности прокачки менять соотношение длительности пачек и пауз между ними. Если бы не пара нюансов.
1. Пьезоэлектрическая сущность новой качалки выливается в очень узкую полосу рабочих частот. Буквально 150-200Гц вправо-влево и качалка превращается в бестолковую шипелку и даже в стакане воды на глубине 2-3 см не может выдавить пузырик.
2. Рабочая частота 25,4кГц. С учетом п.1 получаем полосу в районе 25250-25600Гц.
Вроде бы, «как два пальца об асфальт». Заряжаем таймер, вешаем на хардварный выход одной из защелок нашу
Однако, не все так просто.
Во-первых, устройство серийное, а все хардварные выходы таймера B по несчастливой случайности были отданы под управление светодиодами. То есть, без хирургического вмешательства не обойтись. Оставшийся таймер А отдан целиком под задачу измерения, формирует хардварно серии импульсов с заданными параметрами.
Устройство достаточно сложное, и отдавать целый таймер под тупую генерацию монотонных импульсов совсем не хочется. Не говоря уже о том, что для отсчета системных временных интервалов остается только таймер вочдога с весьма скудными возможностями для выбора длительности генерируемых интервалов (одного из четырех жестко заданных).
Я уже был морально готов резать несчастного пациента и кромсать программу, как вдруг вспомнил про неиспользуемый UART1. Вернее, он когда-то использовался в качестве дебажного вывода на консоль. И в первую очередь почему-то мысль мелькнула про мастер-режим SPI. Если взять выход тактовой частоты (UCLK1), то при записи в буферный регистр данных какого-либо байта на данном выходе должна появиться пачка из 8 импульсов, тактирующих передачу. Далее разрешаем прерывание от UTXIFG (по опустошению буфера передатчика), и в нем кидаем в буфер новый байт (неважно, какой).
Дополнительный профит заключается в том, что можно в прерывании подсчитывать количество выданных байт, регулируя таким образом длительность пачки. Частота выходных импульсов устанавливается 16-разрядным счетчиком/делителем, и в этом отношении наш новоявленный «таймер» вполне идентичен обычному таймеру А или В.
Воодушевившись данной идеей, переделал плату (пришлось временно пожертвовать выходом на звуковую пищалку, который неудачно совпал с UCLK1) и стал пробовать. И все бы ничего, если бы не одно досадное обстоятельство: UART-SPI вставляет между байтами паузу в 2 такта. На слух это ощущается в виде противного писка в районе 3кГц (сама рабочая частота ухом не воспринимается) — это частота следования байтов. Учитывая, что данные дозаторы могут стоять в одном помещении десятками, заценил «какофонию», проникся жалостью к обслуживающему персоналу и стал искать другие пути.
А другой путь обозначился практически сразу же. Надо использовать не тактовые импульсы, а информационный выход. И не SPI, а UART.
То есть, привычный старт-стопный формат с одним стоповым битом и 0x55 в качестве информационного наполнения. Тактовую частоту UARTа нужно задавать в виде удвоенной выходной. Как оказалось, это был наилучший выбор из всех возможных. Во-первых, байты следуют без разрывов (видимо, в это время формируются стартовый и стоповый биты). Во-вторых, не пришлось ничего резать, т.к. UTXD1 был выведен только на тестовый разъём — осталось только кинуть перемычку в нужное место. Ну, и в заключение — в отличие от таймера и SPI, MSP-шный UART умеет формировать дробные битрейты с помощью специального регистра модулятора MCTL. А я неспроста вначале говорил про 25кГц.
Проведем несложный расчет:
тактовая частота от кварца — 4МГц.
делитель U1BR = 78; Fт = 51 282; Fout = 25 641;
делитель U1BR = 79; Fт = 50 632; Fout = 25 316;
делитель U1BR = 80; Fт = 50 000; Fout = 25 000;
Итого, дискретность установки частоты превышает 300Гц, что может оказаться неприемлемым при необходимости тонкой подстройки.
Модулятор повышает точность настройки частоты практически на порядок.
В сухом остатке, имеем выход «ненужного» UARTa, генерирующий нужную частоту, и следующий программный код:
/** Инициализация UART
* FREQ - частота, Гц
*/
void SetUart1(unsigned int FREQ)
{
U1CTL = CHAR | SWRST ; // 8bit, UART, reset
U1TCTL = SSEL_2; // en SMCLK to uart1
U1RCTL =0;
unsigned int freq = (SMCLK + (FREQ))/ (FREQ*2);
U1BR0 = freq & 0xFF; // low byte
U1BR1 = (freq >> 8) & 0xFF; // hi byte
U1MCTL = 0x00;
U1IFG &= ~(URXIFG1 | UTXIFG1); // clear flag RXD
ME2 |= UTXE1; // en TXD
U1CTL &= ~SWRST; // no_reset
IE2 |= UTXIE1; // en ISR
com_dir |= TxD; // configure out port
com_sel |= TxD;
}
И ещё немножко:
/** UART TX ISR */
interrupt (USART1TX_VECTOR) usart1tx_int(void)
{
U1TXBUF = 0x55;
}
Запускаем:
SetUart1(25300);
U1TXBUF = 0x5a;
… и понеслась!
Из данной истории можно вывести два следствия.
1. При желании и(ли) острой необходимости UART вполне может заменить таймер, как для задания временных интервалов, так и для вывода их наружу в виде импульсов.
То есть, теперь я уже вижу, что мог со спокойной душой взять вожделенные импульсы с выхода таймера, а системные тики формировать с помощью прерывания от UARTа.
2. При некоторой сноровке можно организовать ШИМ (в каментах уже написали)
Напоследок, вследствие прилива положительных эмоций, решил немного поглумиться:
#define NOTE_DO 523
#define NOTE_RE 587
#define NOTE_MI 659
#define NOTE_FA 698
#define NOTE_SO 784
#define NOTE_LA 880
#define NOTE_SI 988
#define NOTE_DO2 1046
static const unsigned int Notes[8] = {
NOTE_DO,
NOTE_MI,
NOTE_SO,
NOTE_DO2,
NOTE_DO2,
NOTE_SO,
NOTE_DO2,
NOTE_DO2
};
//...
//----------------- Включение питания ----------------------------
PowerOn();
/** Музыкальная пауза */
for(int i = 0; i<8; i++)
{
SetUart1(Notes[i]);
Delay(100);
ClearWatchDog();
}
//------------------------
- +2
- 19 января 2012, 17:53
- MrYuran
Я когда был маленький и еще не знал что такое МК и UART, делал как-то ШИМ на КОМ порту компьютера. На TX диод, RC фильтр и на варикап УКВ приёмника. Сигнал точной настройки приемника через ключ на RI. И была прога, которая этим чудом рулила и осуществляла автонастройку на станции. Правда, когда комп сильно нагружался, частота отправки байтов в КОМ порт падала и настройка уезжала.
На вид — как обычная пьезопищалка, только чуть потолще и с обратной от кристалла стороны закрыта пластмассовым корпусом с дырочкой посередине.
Все, что она делает — колеблет (колебает?) воздух мембранкой туда-обратно.
Ставим снаружи клапан типа «лягушка» — получаем качалку.
Работает практически бесшумно, не считая шипения воздуха. Но по сравнению с «б-рррр, б-рррр» прошлой качалки (простая катушка с магнитной мембранкой) это «п-шшш, п-шшш» просто за счастье. К тому же стоит в 4 раза дешевле (500р против 2000р российского производства и 150-200 евро немчура). Новая — типа яповская.
Ещё один профит — легкость замены.
Все, что она делает — колеблет (колебает?) воздух мембранкой туда-обратно.
Ставим снаружи клапан типа «лягушка» — получаем качалку.
Работает практически бесшумно, не считая шипения воздуха. Но по сравнению с «б-рррр, б-рррр» прошлой качалки (простая катушка с магнитной мембранкой) это «п-шшш, п-шшш» просто за счастье. К тому же стоит в 4 раза дешевле (500р против 2000р российского производства и 150-200 евро немчура). Новая — типа яповская.
Ещё один профит — легкость замены.
Гм. Ты не совсем меня понял) Перефразирую.
Запили, плиз, про эту помпу статью в блог «Деталька». С фоточками и всем-всем-всем. Заодно и где купить.
Алсо, что у вас там эта помпа делает?
Запили, плиз, про эту помпу статью в блог «Деталька». С фоточками и всем-всем-всем. Заодно и где купить.
Алсо, что у вас там эта помпа делает?
У нас там эта помпа дозирует реактив. Прокачивает пузыри воздуха через аммиак, а выходящие из ёмкости пары аммиака пузырятся в жидкость, подщелачивая её.
Подробнее пока вряд ли, т.к на эксперимент купили всего 5 штук, и они все уже упакованы в корпуса и поставлены на прогон. Разве что потом, когда в серию пойдет.
Подробнее пока вряд ли, т.к на эксперимент купили всего 5 штук, и они все уже упакованы в корпуса и поставлены на прогон. Разве что потом, когда в серию пойдет.
как-то раз понадобилось использовать передатчик spi в для передачи в данных в радиомодуль, у которого передача была своеобразно устроена: просто выведена нога управления модулятора, на приёме-то он сам клоки восстанавливал и данные по spi зачитать можно было.
но вот с передачей в MSP оказалось что при непрерывном запихивании данных в USCI вроде (не помню правда точно что именно там было) наружу они лезли не непрерывно, а с паузой в один бит между ними, что немного портило картину на приёме, потому что вместо 8 бит приходило девять, а spi ему всё равно, пока клоки и cs есть принимает байты подряд.
пришлось забирать их как есть в некий буфер, а потом лазить по нему и руками двигать и убирать лишние биты.
такие вот замечательные грабли.
но вот с передачей в MSP оказалось что при непрерывном запихивании данных в USCI вроде (не помню правда точно что именно там было) наружу они лезли не непрерывно, а с паузой в один бит между ними, что немного портило картину на приёме, потому что вместо 8 бит приходило девять, а spi ему всё равно, пока клоки и cs есть принимает байты подряд.
пришлось забирать их как есть в некий буфер, а потом лазить по нему и руками двигать и убирать лишние биты.
такие вот замечательные грабли.
Комментарии (8)
RSS свернуть / развернуть