Синтезатор частоты AD9832 на базе SPI STM32F2xx
Синтезатор частоты AD9832 довольно таки избитая тема. И тем не менее время от времени приходится возвращаться к DDS для проведения тех или иных тестов. В данном посте описан один из возможных способов управления DDS AD9832 с помощью SPI нтерфейся микроконтроллера STM32F2xx. Такой вариант достаточно удобен, поскльку позволяет посылать команды на AD9832 в виде 16 битных слов с нужным расположением битов - старшими вперед.
Прежде чем привести простейший код инициализации SPI STM32F2xx для работы с синтезатором частоты AD9832 полезно пройтись по интерактивным программам позволяющим не только рассчитать и представить код соответствующий нужной частоте, который нужно загружать в регистры частоты DDS, но и представить предполагаемый спектр сформированного с помощью DDS сигнала.
Итак простейший вариант формирования синусоидального сигнала на базе DDS AD9832 это последовательное выполнение нескольких команд по сбросу, загрузке регистров частоты и пуску DDS. Для более полной информации ниже представлена картинка со стандартной схемой подключения AD9832.
C14 - 100 nF, C23 - 100 nF, R8 - 50 Ohm (выход сигнала), R7 - 300 Ohm, R6 - 3,9 k, C18 - 10 nF, C17 - 10 nF
1 - Корпус. Аналоговое и цифровое питание на девайсик можно подавать от одного источника напряжения через резисторы 50...100 Ohm
Для примера, чтобы получить выходную частоту 1 КГц - при MCLK 12,5 мГц порядок загрузки Ad9832 будет следующий:
0xF800 - сброс
0x 3300 - загрузка регистра FREQ0 REG 8 H MSBs
0x2205 - загрузка регистра FREQ0 REG 8 L MSBs
0x313e - загрузка регистра FREQ0 REG 8 H LSBs
0x202d - загрузка регистра FREQ0 REG 8 L LSBs
0xc000 - пуск синтезатора
При этом загрузка каждого слова должна сопровождаться отрицательным сигналом на входе FSYNC. В дальнейшем перестройка DDS осуществляется только загрузкой нужных регистров частоты. Поскольку выходная частота рассчитывается как:
Fout = FREG0 * Fmclk / 2^32, где
Fout - частота на выходе dds, Hz;
FREG0 - значение регистра, определяющего частоту (32 бит);
Fmclk - тактовая частота dds, Hz;
2^32 = 4 294 967 296.
Решая это простое уровнение относительно FREG0, находим:
FREG0 = (Fout / Fmclk) * 2^32;
И для частоты 1 kHz
FREG0 = (1 000 /12 500 000) * 2^32 = 343597 = 0x00053e2d.
Итак функция инициализации SPI3
void SPI3_Init(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
SPI_InitTypeDef SPI_InitStructure;
// Output HSE clock (12.5 MHz) on MCO pin (PC9) to clock the AD9832
RCC_MCO2Config(RCC_MCO2Source_HSE, RCC_MCO2Div_2);
// PC11 - NSS софтовый PС10 - SPI3 SCK PС12 - SPI3 MOSI
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOC, ENABLE);
RCC_APB1PeriphClockCmd(RCC_APB1Periph_SPI3, ENABLE);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_Init(GPIOC, &GPIO_InitStructure);
GPIO_PinAFConfig(GPIOC, GPIO_PinSource9, GPIO_AF_MCO);
// NSS: выход push-pull
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOC, &GPIO_InitStructure);
// SCK: выход push-pull
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOC, &GPIO_InitStructure);
GPIO_PinAFConfig(GPIOC, GPIO_PinSource10, GPIO_AF_SPI3);
// MOSI: выход push-pull
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOC, &GPIO_InitStructure);
GPIO_PinAFConfig(GPIOC, GPIO_PinSource12, GPIO_AF_SPI3);
// SPI Init
SPI_InitStructure.SPI_Direction = SPI_Direction_1Line_Tx;
SPI_InitStructure.SPI_Mode = SPI_Mode_Master;
SPI_InitStructure.SPI_DataSize = SPI_DataSize_16b;
SPI_InitStructure.SPI_CPOL = SPI_CPOL_Low;
SPI_InitStructure.SPI_CPHA = SPI_CPHA_2Edge;
SPI_InitStructure.SPI_NSS = SPI_NSS_Soft;
SPI_InitStructure.SPI_BaudRatePrescaler = SPI_BaudRatePrescaler_256;
SPI_InitStructure.SPI_FirstBit = SPI_FirstBit_MSB;
SPI_Init(SPI3, &SPI_InitStructure);
SPI_Cmd(SPI3, ENABLE);
}
Ну и собственно функция загрузки AD9832
void SPI3_WriteWorld(int Data)
{
Delay(10);
// FSYNC в 0
GPIOC->ODR &= ~GPIO_OTYPER_ODR_11;
// Отправка данных (16 бит)
SPI_I2S_SendData(SPI3, Data);
// Жду пока буфер TX будет пустой
while (SPI_I2S_GetFlagStatus(SPI3, SPI_I2S_FLAG_TXE) == RESET)
// Задержка подбирается
Delay(2500);
// FSYNC в 1
GPIOC->ODR |= GPIO_OTYPER_ODR_11;
}
Данный код проверен на работоспособностьв демопроекте LwIp стека под платку SK-STM32F217
Электроника :
- Техника электроника (11)
- Полезная электроника (4)
- Электроника для всех (5)
- Техника для дома (6)
- Cхемотехника ПЛИС (11)
- Пректирование PCAD (4)
Программирование :
- Микроконтроллеры (9)
- ПЛИС VHDL Verilog (29)
- C++ Builder (7)
- Visual Studio C++ C# (7)
- Java programming (7)
- Matlab programming (4)
Сайтостроение :
- Сайтостроение HTML (5)
- Сайтостроение PHP (8)
- PHP CMS на файлах (3)
- Web инструменты (9)
- Полезное вебмастеру (11)
- SEO раскрутка сайта (4)
- PHP скрипты (3)
Реклама :
Книги и учебники :
- Шаблоны сайтов (6)
- Книги и учебники (2)
Компьютер и интернет :
Поиск по сайту :
Реклама :
Облако меток :
Бесплатная подписка :
Статистика :
- Популярность (3)
- Посещаемость (3)
- Поисковые запросы (3)