|
Нелинейности внутреннего АЦП в STM32, STM32F103RET6 GH22S 9U |
|
|
|
Feb 25 2014, 09:09
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
И так работаю с контроллером STM32F103RET6 GH22S 9U (это полная маркировка, вдруг важно), работаю на частоте 72 МГц, и вот какая проблема, не зависимо от времени семплирования и настроек АЦП при подачи на вход плавно меняющейся функции (и сигнал с датчика температуры - терморезистора, так и просто источник опорного напряжения регулируемый пробовал) на выходи имеем нелинейности - ступеньки на определенных значениях, см. вложение. И так поиск по интернету не дал ответа на вопрос что это и как исправлять (ну кроме смены процессора, просто неисправность камня я исключил так как попробовал на двух идентичных контроллерах), положение ступенек не зависит от напряжения, то есть при изменении опорного напряжения ступеньки остаются в тех же точках, хоть это уже другие напряжения, точки в которых есть ступеньки характерные, в них одновременно сменяется сразу много разрядов (отметил это на графике).
Сообщение отредактировал zWitCh - Feb 25 2014, 09:10
|
|
|
|
|
 |
Ответов
(1 - 64)
|
Feb 25 2014, 14:30
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Цитата(scifi @ Feb 25 2014, 15:56)  Вы, видимо не в курсе, что такое автоматическая калибровка АЦП в STM32F1xx. Процедура калибровки пройдена, на вход АЦП подаю напряжение с лабораторного источника, плавно его меняю, АЦП выдает совершенно точно оцифрованные значения, так что калибровка не только пройдена но и пройдена видимо успешно, что касается программной ошибки, то все замечательно работает пока на вход не подаше некое напряжение равное в цифровом выражении "1023" и вот тогда АЦП перестает чувствовать малые изменения входного сигнала постоянно выдавая "1023". Цитата(Aner @ Feb 25 2014, 15:32)  Программная проблема, разбирайтесь с прерываниями и записью в регистры. "missing code" SAR ADC - это немного не то, тут нет этого. Прерывания отключены, запись в регистр пишу не я а АЦП, я из него просто читаю в бесконечном цикле, придумайте мне хотя бы синтетический пусть невероятный но все же пример при котором АЦП будет выдавать ступенчатую характеристику только для определенного диапазона (очень узкого) а в остальном диапазоне работать идеально? думаю при всей фантазии такой пример будет придумать сложно ;-)
Сообщение отредактировал zWitCh - Feb 25 2014, 14:35
|
|
|
|
|
Feb 25 2014, 15:41
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Цитата(Aner @ Feb 25 2014, 18:59)  Схему, прогу в студию. Телепатов пока нема. Может глюк связан с источником питания и наведенной гармоникой, если плохо отвязка сделана. Программно как сделано? Смотрите в дебаге или как? .. Проблема с циклом? ... читаю в бесконечном цикле -> и куда дале и как вывод данных делается? И так на ножке PC5 через резистор в 10к подключен лабораторный источник более ничего нет в схеме, минимальная обвязка со всеми рекомендованными блокирующими конденсаторами, подаю напряжение от полвольта до 2 вольт плавно регулируя вход, параллельно на входе висит осциллограф и мультиметр, и на том и на том приборах напряжения меняются плавно, нет ни всплесков, ни помех (осциллограф с 100 Мгц полосой пропускания, смотрю на хорошей развертке). Смотрю в консоле по СОМ порту. Питание платы идет от стабилизированного источника (другого, лабораторника, земли СОЕДИНЕНЫ). Питание первое что проверил, там все чисто настолько на сколько дает мне понять мой осциллограф. Код: CODE #include<stm32f10x_rcc.h> #include<stm32f10x_gpio.h> #include "stm32f10x.h" #include "stm32f10x_usart.h"
void _debug_print_byte(char c){ while(!(USART1->SR & USART_SR_TC)); USART1->DR = c; }
void _debug_print_str(char *s){ do{ _debug_print_byte(*s); }while(*(++s)); }
void _debug_print_num(uint16_t var){ char c, s[6], *p_s = &s[0], *p2_s; uint8_t i, j = 0;
do { *p_s++ = var % 10 + '0'; j++; } while ((var /= 10) > 0); *p_s = '\0';
for (i = 0, p_s--, p2_s = &s[0]; i<j; i++, j--) { c = *p2_s; *p2_s++ = *p_s; *p_s-- = c; } _debug_print_str(s); }
int main(void) {
uint32_t i; GPIO_InitTypeDef PORT;
// Initialize USART1 USART_InitTypeDef USART_InitStructure; GPIO_InitTypeDef PORT; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB | RCC_APB2Periph_AFIO, ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE); AFIO->MAPR |= AFIO_MAPR_USART1_REMAP; PORT.GPIO_Pin = GPIO_Pin_6; PORT.GPIO_Speed = GPIO_Speed_2MHz; PORT.GPIO_Mode = GPIO_Mode_AF_PP; GPIO_Init(GPIOB, &PORT);
USART_InitStructure.USART_BaudRate = 115200; USART_InitStructure.USART_WordLength = USART_WordLength_8b; USART_InitStructure.USART_StopBits = USART_StopBits_1; USART_InitStructure.USART_Parity = USART_Parity_No; USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; USART_InitStructure.USART_Mode = USART_Mode_Tx; USART_Init(USART1, &USART_InitStructure); USART_Cmd(USART1, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC , ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2ENR_ADC1EN, ENABLE); ADC1->CR2 |= ADC_CR2_CAL; while (!(ADC1->CR2 & ADC_CR2_CAL)) ADC1->CR1 |= ADC_CR1_SCAN; ADC1->CR2 |= ADC_CR2_EXTSEL; ADC1->CR2 |= ADC_CR2_EXTTRIG; ADC1->SQR3 |= (ADC_SQR3_SQ1_3|ADC_SQR3_SQ1_2|ADC_SQR3_SQ1_1|ADC_SQR3_SQ1_0); ADC1->CR2 |= ADC_CR2_ADON; ADC1->CR2 |= ADC_CR2_SWSTART; while (!(ADC1->SR & ADC_SR_EOC)); while(1) { i = 0xffff; while(i--); ADC1->CR2 |= ADC_CR2_SWSTART; while (!(ADC1->SR & ADC_SR_EOC)); _debug_print_num(ADC1->DR); _debug_print_str("\r\n");
} } Кратенько суть того что делает программа вот: CODE int main(void) { uint32_t i; GPIO_InitTypeDef PORT;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC , ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2ENR_ADC1EN, ENABLE); ADC1->CR2 |= ADC_CR2_CAL; while (!(ADC1->CR2 & ADC_CR2_CAL)) ADC1->CR1 |= ADC_CR1_SCAN; ADC1->CR2 |= ADC_CR2_EXTSEL; ADC1->CR2 |= ADC_CR2_EXTTRIG; ADC1->SQR3 |= (ADC_SQR3_SQ1_3|ADC_SQR3_SQ1_2|ADC_SQR3_SQ1_1|ADC_SQR3_SQ1_0); ADC1->CR2 |= ADC_CR2_ADON; ADC1->CR2 |= ADC_CR2_SWSTART; while (!(ADC1->SR & ADC_SR_EOC)); while(1) { i = 0xffff; while(i--); ADC1->CR2 |= ADC_CR2_SWSTART; while (!(ADC1->SR & ADC_SR_EOC)); _debug_print_num(ADC1->DR); _debug_print_str("\r\n");
} } Сразу отмечу что время семплирования не влияет, ставил разное, делал то же самое но через инжектированные каналы, эффект тот же... Цитата(scifi @ Feb 25 2014, 18:40)  А может, лучше чуть пореже читать? Вдруг там что-то клинит от частого считывания? чуть выше код того как я делаю, тут мало того что не очень то и часто читается, но и читается только когда данные готовы, так что нет, дело не в чтении (да и чтение бы проявлялось не так, у меня сто процентная повторяемость на определенном значении (нескольких значениях) выдаваемых АЦП, при этом если подать опору другую и АЙП будет выдавать 1023 при другом входном напряжении, все равно ступенька именно в тех же точках оцифрованных, то есть это никак не связано с чтением или входом судя по всему...)
Сообщение отредактировал IgorKossak - Feb 25 2014, 17:46
Причина редактирования: [codebox] для длинного кода, [code] - для короткого!!!
|
|
|
|
|
Feb 26 2014, 11:11
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
продолжил свои изыскания, взял я совершенно другую плату (на STM32F103RBT6):
проводами на один из входов подключил источник питания регулируемый, и начал плавно его регулировать попутно записывая все измерения (код программы тот же что и ранее), вот что вышло:
Вроде все хорошо, помехи и выбросы есть и на осциллограмме, они связаны с тем что источник плохой и длинными проводами подключен, но если рассмотреть участок вблизи моей злополучной точке "1023" то мы увидим все ту же проблему:
Тут хорошо видно что вблизи точки "1023" (значение выдаваемое АЦП) полностью отсутствуют значения в диапазоне от 1024 до 1048 и все они заменяются на мои 1023! Дальше я просто посмотрел а АЦП хоть когда либо выдает ли мне на выходе цифры в диапазоне 1024 - 1048, и выяснились что нет, на двух совершенно разных платах и немного разных процессорах... Обнаружив такую особенность я достал старую добрую STM32-Discovery и запустил тот же код на ней, там все ок, таких особенностей работы АЦП не заметил...
|
|
|
|
|
Feb 26 2014, 11:56
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Цитата(ViKo @ Feb 26 2014, 15:19)  Так не в источнике питания ли дело? Что, если подать питание через дроссель, LC фильтр? Там помехи бегают... Интересные помехи которые распределены во всем диапазоне равномерно а в определенных точках отсутствуют и сигнал в них идеально гладкий, ну да ладно, пошел дальше в изысканиях, немного переписал код, теперь я просто считаю сколько раз я с выхода АЦП имею определенное значение, а на вход подал просто шум, ниже код и результат. Код uint16_t arr[4096], indx;
int main(void) {
uint32_t i; GPIO_InitTypeDef PORT;
// Initialize USART1 (для рабочей платы) /* USART_InitTypeDef USART_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB | RCC_APB2Periph_AFIO, ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE); AFIO->MAPR |= AFIO_MAPR_USART1_REMAP; PORT.GPIO_Pin = GPIO_Pin_6; PORT.GPIO_Speed = GPIO_Speed_2MHz; PORT.GPIO_Mode = GPIO_Mode_AF_PP; GPIO_Init(GPIOB, &PORT); //*/
// Initialize USART1 (для стартика MINI_STM32_V3) USART_InitTypeDef USART_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE); PORT.GPIO_Pin = GPIO_Pin_9; PORT.GPIO_Speed = GPIO_Speed_2MHz; PORT.GPIO_Mode = GPIO_Mode_AF_PP; GPIO_Init(GPIOA, &PORT);
USART_InitStructure.USART_BaudRate = 115200; USART_InitStructure.USART_WordLength = USART_WordLength_8b; USART_InitStructure.USART_StopBits = USART_StopBits_1; USART_InitStructure.USART_Parity = USART_Parity_No; USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; USART_InitStructure.USART_Mode = USART_Mode_Tx; USART_Init(USART1, &USART_InitStructure); USART_Cmd(USART1, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC , ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2ENR_ADC1EN, ENABLE); ADC1->CR2 |= ADC_CR2_CAL; while (!(ADC1->CR2 & ADC_CR2_CAL)) ADC1->CR1 |= ADC_CR1_SCAN; ADC1->CR2 |= ADC_CR2_EXTSEL; ADC1->CR2 |= ADC_CR2_EXTTRIG; ADC1->SQR3 |= (ADC_SQR3_SQ1_3|ADC_SQR3_SQ1_2|ADC_SQR3_SQ1_1|ADC_SQR3_SQ1_0); // вход AN15 ADC1->CR2 |= ADC_CR2_ADON; ADC1->CR2 |= ADC_CR2_SWSTART; while (!(ADC1->SR & ADC_SR_EOC)); _debug_print_str("\r\n *** TEST *** \r\n");
while(1) { ADC1->CR2 |= ADC_CR2_SWSTART; while (!(ADC1->SR & ADC_SR_EOC));
indx = ADC1->DR; if(arr[indx] < 0x1FFF) arr[indx]++; if(arr[4090] > 100) break; }
i = 4096; while(i--){ _debug_print_num(i); _debug_print_str(";"); _debug_print_num(arr[i]); _debug_print_str(";\r\n");
} while(1); } И вот что мы имеем на выходе:
Тут отчетливо видно что есть значения которые АЦП на выходе не выдает никогда, я лично очень сомневаюсь что тот сигнал что я подавал на вход (шум), действительно имеет такие дырки (я его формировал крутя потенциометр в зад - перед раз 20, в конце выкрутил в крайнее положение и мой код отследил приход значений соответствующих крайнему положению и выдал результат в UART).
|
|
|
|
|
Feb 26 2014, 12:35
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Цитата(ViKo @ Feb 26 2014, 16:10)  На Дискавери нет источника. Она от USB питается. И провалов в кодах с АЦП, по уверению автора, на ней нет. на дискавери есть источник: L1117 Series но это не суть, моя плата по схемотехники запитана аналогичным с дискавери образом, через линейный преобразователь, Помехи идет в лилии сигнальной, уровень этих помех мал что видно на графике, да и исходно я обнаружил данный феномен на плате где сигнал не так зашумлен, мы сейчас обсуждаем на сколько чистый я сигнал оцифровываю, но я сейчас в рамках проверки АЦП оцифровываю шум, шум этот малой амплитуды (меньше чем питание АЦП), так что не очень понял причем тут помехи по питанию, в начале топика я уже писал, что питание проверил первым, в нем нет выбросов и провалов. Цитата(scifi @ Feb 26 2014, 16:28)  +1. Кстати, в том же AN2586 сказано, что для фильтрации можно добавить ferrite bead перед Vdda и резистор перед Vref. Господа, пожалуйста будте внимательнее, у меня все блокирующие конденсаторы и дросели у VADD стоят, в цепи питания НЕТ ПОМЕХ! Зашумел помехой я сигнал который оцифровываю специально для эксперимента, что бы поиметь на выходе с АЦП более менее нормальное распределение!
|
|
|
|
|
Feb 26 2014, 12:36
|

Универсальный солдатик
     
Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362

|
Цитата(zWitCh @ Feb 26 2014, 15:35)  ...так что не очень понял причем тут помехи по питанию, в начале топика я уже писал, что питание проверил первым, в нем нет выбросов и провалов. ... Господа, пожалуйста будте внимательнее, у меня все блокирующие конденсаторы и дросели у VADD стоят, в цепи питания НЕТ ПОМЕХ! Зашумел помехой я сигнал который оцифровываю специально для эксперимента, что бы поиметь на выходе с АЦП более менее нормальное распределение! А это не вы писали: "Вроде все хорошо, помехи и выбросы есть и на осциллограмме, они связаны с тем что источник плохой и длинными проводами подключен"? Чудеса...
|
|
|
|
|
Feb 26 2014, 12:37
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Цитата(Tanya @ Feb 26 2014, 16:04)  Источник бы везде. Он ведь не знает про цифры внутри... А вот если построить график напряжение - код-напряжение(как будто подсоединен виртуальный ЦАП), то что будет? Будут ли две прямые со сдвигом - до и после магического числа? Если так, то калибровка внутри сбита - этот разряд значительно больше нормального и компаратор уже не добавляет несколько младших. вот тут была картинка в самом начале:
там наглядно показано что выдает (оцифровывает АЦП), на входе напряжение при этом меняется линейно (проверено осциллографом на хорошей развертке)
|
|
|
|
|
Feb 26 2014, 12:39
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Цитата(ViKo @ Feb 26 2014, 16:36)  А это не вы писали: "Вроде все хорошо, помехи и выбросы есть и на осциллограмме, они связаны с тем что источник плохой и длинными проводами подключен"? Чудеса...  источник СИГНАЛА который я подаю на вход ЦАП, и да это я написал, слово источник не всегда источник питания тем более когда оговорено иное...
|
|
|
|
|
Feb 26 2014, 12:41
|

Универсальный солдатик
     
Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362

|
Цитата(zWitCh @ Feb 26 2014, 15:37)  (проверено осциллографом на хорошей развертке) ШУМИТ... или источник питания, или опорного напряжения (если оно есть), или измеряемый сигнал. На таких частотах, или импульсы короткие, так, что вы их не видите своим осциллографом. Цитата(zWitCh @ Feb 26 2014, 15:39)  источник СИГНАЛА который я подаю на вход ЦАП, и да это я написал, слово источник не всегда источник питания тем более когда оговорено иное... ах, если СИГНАЛА, тогда его и фильтруйте! Сами путаете: "проводами на один из входов подключил источник питания регулируемый, и начал плавно его регулировать попутно записывая все измерения"
|
|
|
|
|
Feb 26 2014, 12:42
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Цитата(Tanya @ Feb 26 2014, 16:39)  А вход опорного напряжения имеет адекватный конденсатор? А на входе? вход Vref отсутствует в моем корпусе, на входе Vdda стоит 10u и 0.1u плюс дроссль
|
|
|
|
|
Feb 26 2014, 12:56
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Цитата(Tanya @ Feb 26 2014, 16:41)  Нет, я не то хотела. Подгонку линейной функцией до и после. И вот эти числа. На глаз не видно по Вашим картинкам. ну я уже новые данные поимел я подовая на вход ШУМ имею кучу значений разных с АЦП, так вот среди этих значений отсутствуют определенные значения всегда, в частности там нет цифр в промежутке 1024-1048, что мне кажется просто невероятным что бы в течении получаса сыпался условно случайный сигнал и в нем ниразу не встретилось напряжение эквивалентное значению с 1024 по 1048 но при этом все другие встречаются великое множество раз... Цитата(ViKo @ Feb 26 2014, 16:41)  ШУМИТ... или источник питания, или опорного напряжения (если оно есть), или измеряемый сигнал. На таких частотах, или импульсы короткие, так, что вы их не видите своим осциллографом.
ах, если СИГНАЛА, тогда его и фильтруйте!
Сами путаете: "проводами на один из входов подключил источник питания регулируемый, и начал плавно его регулировать попутно записывая все измерения" источник питания подключен на вход АЦП, отдельный источник питания в качестве сигнала, который я оцифровываю, даже не понимаю как еще это можно объяснить что бы стало понятно, батарейку я если подключу на вход АЦП это же не как не будет значить что мой ацп питается от батарейки, я беру ее напряжение как сигнал... фу... все не по теме... Зачем мне фильтровать сигнал, меня не смущают момехи, напротив меня смущает то что АЦП не при каких входных напряжениях не выдает на выходе скажем "1030" или "1035" и еще пару десятков значений, как это связано с питанием которое мало того что независимое так еще и чистое, ок, допустим помехи, что это за такие синхронные помехи которые сбивают именно АЦП и именно тогда когда он хзочет выдать любую цифру в промежутке от 1024 до 1048 но при этом НИКОГДА не сбивают его в других случаях и в других значениях его передаточная функция гладкая...
|
|
|
|
|
Feb 26 2014, 13:11
|

Универсальный солдатик
     
Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362

|
Цитата(zWitCh @ Feb 26 2014, 15:56)  Зачем мне фильтровать сигнал, меня не смущают момехи, напротив меня смущает то что АЦП не при каких входных напряжениях не выдает на выходе скажем "1030" или "1035" и еще пару десятков значений, как это связано с питанием которое мало того что независимое так еще и чистое, ок, допустим помехи, что это за такие синхронные помехи которые сбивают именно АЦП и именно тогда когда он хзочет выдать любую цифру в промежутке от 1024 до 1048 но при этом НИКОГДА не сбивают его в других случаях и в других значениях его передаточная функция гладкая... Еще раз внушаю - импульсные помехи лезут в АЦП, неважно, каким путем, и сбивают механизм последовательного приближения. Если должен быть код 1026, а старший разряд не установился, потому что помеха в момент его определения сбила его в 0, то больше 1023 уже не набрать.
|
|
|
|
|
Feb 26 2014, 13:43
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Цитата(Tanya @ Feb 26 2014, 17:36)  Какая-то у Вас очень проницательная (избирательная) помеха. да вот и я о том же, вобщем пока мы тут общались на вход АЦП гнал я псевдослучайный сигнал (пилу с генератора), затем вывел всё что оцифровывал мне мой АЦП, так вот в его результатах напрочь отсутствует целая груда значений, то есть при любом входе он никогда не выдает определенные цифры на выходе...
На данной диаграмме хорошо видно что определенные значения я на выходе у АЦП не получаю никогда, хотя на входе была достаточно гладкая функция без разрывов... Цитата(ViKo @ Feb 26 2014, 17:11)  Еще раз внушаю - импульсные помехи лезут в АЦП, неважно, каким путем, и сбивают механизм последовательного приближения. Если должен быть код 1026, а старший разряд не установился, потому что помеха в момент его определения сбила его в 0, то больше 1023 уже не набрать. да все верно, только вот что это за помеха то такая которая сбивает только когда у меня ацп хочет выдать 1024 - 1049 (и еще пары диапазонов которые всегда одни и теже и мало вообще от чего зависят, просто есть) но никогда не сбивает при других выходных значениях, при этом источник питания и источник сигнала независимы и питание чистое...
Сообщение отредактировал zWitCh - Feb 26 2014, 13:45
|
|
|
|
|
Feb 26 2014, 14:16
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Цитата(Tanya @ Feb 26 2014, 17:56)  Так можете тактовую частоту понизить на порядок? Я даже догадываюсь, где еще сбоит. и так, теперь я вместо 72 МГц по дефолту, ставлю принудительно частоту как на Дискавери - 24 МГц и о чудо, помехи уже ничего не сбивают ни по питанию не по сигнальной шине, АЦП магическим образом обретает гладкую характеристику... данные с АЦП при частоте 72 Мгц на ядре, хорошо видно дырки, определенные значения не выдаются АЦПхой не при каких входных воздействиях:
Данные с АЦП на частоте 24 Мгц, характеристика гладкая, нет дырок, всем входным воздействиям есть выходной аналог:
Что выходит что АЦП не успевал работать, или вернее не успевал заряжать свои внутренние конденсаторы и из-за этого сбоил если надо было сменить сразу много разрядов? Как бороться кроме понижения частоты, может таки оптимизировать разводку?
Сообщение отредактировал zWitCh - Feb 26 2014, 14:17
|
|
|
|
|
Feb 26 2014, 14:39
|
Гуру
     
Группа: Модераторы
Сообщений: 8 752
Регистрация: 6-01-06
Пользователь №: 12 883

|
Цитата(zWitCh @ Feb 26 2014, 18:16)  - 24 МГц и о чудо, помехи уже ничего не сбивают ни по питанию не по сигнальной шине, АЦП магическим образом обретает гладкую характеристику... Я же Вам сразу предлагала... Цитата(zWitCh @ Feb 26 2014, 18:16)  Как бороться кроме понижения частоты, может таки оптимизировать разводку? Правильная разводка и правильные конденсаторы снаружи. А буфер для входного сигнала у Вас есть? Дроссель может даже вредить.
|
|
|
|
|
Feb 26 2014, 14:40
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Занизил частоту ADCCLK поделил на 16, все стало ок... Век живи век учись ;-) Код SystemInit(); RCC_ADCCLKConfig(RCC_PCLK2_Div8); SystemCoreClockUpdate(); PS да буфер есть, достаточно конденсатор на 10мкФ, в боевой схеме мэрию медленно меняющееся напряжение (напряжение на большом ионисторе, так что эти мои 10vrA там просто что бы компенсировать подводящие провода).
Сообщение отредактировал zWitCh - Feb 26 2014, 14:44
|
|
|
|
|
Feb 26 2014, 15:10
|
Участник

Группа: Участник
Сообщений: 19
Регистрация: 18-08-06
Пользователь №: 19 654

|
Цитата(scifi @ Feb 26 2014, 18:45)  Семён Семёныч! :-) Видимо, было превышение ADC clock 14 MHz max... очевидно именно это и произошло по собственному моему недосмотру и забывчивости, зато вот как интересно это проявилось :-)
|
|
|
|
|
Mar 3 2014, 11:50
|

Универсальный солдатик
     
Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362

|
Цитата(Леонид Иванович @ Mar 3 2014, 00:22)  Документ AN3137 во многом повторяет AN2834. Там содержится такое же описание структуры АЦП, и даже та же ошибка в формуле для вычисления периода выборок с большой входной емкостью. У меня в разных местах лежали разные версии этого документа. В первой картинок с конденсаторами не было. Посмотрел вашу статью. Похоже, вы не поняли их совета подключать большой внешний конденсатор. Такой, чтобы напряжение на нем не сильно изменялось при заряде внутреннего конденсатора УВХ, не более, чем половина младшего разряда. Этот совет "вреден" только тем, что сильно уменьшается полоса измеряемого сигнала. Что творится в цепи сигнала до УВХ, значения не имеет (кроме помех соседям, и импульсной нагрузки ОУ). Важно, что мы имеем после УВХ.
|
|
|
|
|
Mar 3 2014, 12:34
|

Местный
  
Группа: Участник
Сообщений: 318
Регистрация: 21-07-06
Из: Минск
Пользователь №: 18 986

|
Цитата(ViKo @ Mar 3 2014, 14:50)  Этот совет "вреден" только тем, что сильно уменьшается полоса измеряемого сигнала. Нет. Этот совет может быть вреден еще и тем, что способен привести к ошибке измерения по постоянному току. Большая емкость на входе АЦП обеспечит среднее значение напряжения, которое будет отличаться от измеряемого на величину Verr = Rin * Iin_avg, где Rin - сопротивление на входе АЦП (вместе с внутренним сопротивлением источника сигнала), Iin_avg - средний входной ток АЦП. Для худшего случая Iin_avg = Vref * Csh * Fs, где Vref - опорное напряжение, Csh - емкость УВХ, Fs - частота выборок АЦП.
--------------------
|
|
|
|
|
Mar 3 2014, 13:06
|

Универсальный солдатик
     
Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362

|
Входной ток у АЦП - это ток заряда внутреннего конденсатора, во время выборки. Если бы напряжения на внешнем и внутреннем конденсаторах были равными, вообще никакого тока не было бы. Это не постоянная величина. Здесь ошибка.
Если источник сигнала (с его внутренним сопротивлением, или дополнительным последовательным резистором) способен зарядить внешнюю большую емкость за время от выборки к выборке, то почему он не справится с суммой внешней и маленькой внутренней? Если не справляется и с внешней - это и есть ограничение полосы.
В AN2834 пишут про то, что заряд с внутренней емкости может подзаряжать внешнюю, если слишком часто делать выборки. Это уже для случая большого сопротивления источника. Но не настолько большого, чтобы не успевать заряжать внешнюю емкость.
Если же говорить о постоянном входном токе АЦП (утечки, и т.п.), то он создает на сопротивлении источника постоянную ошибку. Это уже не зависит от емкостей вообще никак.
|
|
|
|
|
Mar 3 2014, 14:25
|

Местный
  
Группа: Участник
Сообщений: 318
Регистрация: 21-07-06
Из: Минск
Пользователь №: 18 986

|
Цитата(ViKo @ Mar 3 2014, 16:06)  Если бы напряжения на внешнем и внутреннем конденсаторах были равными, вообще никакого тока не было бы. Верно. Но после процесса преобразования заряд внутреннего конденсатора в общем случае не равен начальному, который был в конце выборки. Более того, при мультиплексировании каналов этот заряд зависит от входного напряжения предыдущего канала. Т.е. входной ток есть, и он зависит как от входного напряжения данного канала, так и от входного напряжения предыдущего канала. Цитата(ViKo @ Mar 3 2014, 16:06)  Это не постоянная величина. Здесь ошибка. Понятное дело, что не постоянная, я же написал: "для худшего случая". Цитата(ViKo @ Mar 3 2014, 16:06)  Если источник сигнала (с его внутренним сопротивлением, или дополнительным последовательным резистором) способен зарядить внешнюю большую емкость за время от выборки к выборке Если способен зарядить с точностью до 1/2 LSB, то ошибки нет. Но с повышением частоты выборок появляется ошибка. Я предложил простую формулу, основанную на расчете среднего входного тока АЦП, которая дает оценку максимальной допустимой частоты выборок для конкретного Rin при условии Cext >> Csh. Цитата(ViKo @ Mar 3 2014, 16:06)  Если не справляется и с внешней - это и есть ограничение полосы. Ограничение полосы - это совсем другое. Можно взять две разных RC-цепочки с одинаковым тау, но с разным соотношением R и C. Они будут иметь одинаковую частоту среза. Но одна будет давать погрешность по DC, другая - нет. Это зависит от R. Цитата(ViKo @ Mar 3 2014, 16:06)  Если же говорить о постоянном входном токе АЦП (утечки, и т.п.) Ток утечек я вообще не рассматриваю из-за его малости.
--------------------
|
|
|
|
|
Mar 3 2014, 17:46
|

Универсальный солдатик
     
Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362

|
Цитата(Леонид Иванович @ Mar 3 2014, 17:25)  Я предложил простую формулу, основанную на расчете среднего входного тока АЦП, которая дает оценку максимальной допустимой частоты выборок для конкретного Rin при условии Cext >> Csh. Нужно вот как считать. Внутренний конденсатор в конце преобразования Csh заряжен до некоего значения (наверное, до половины опорного), имеет заряд Q = Uh * Csh В режиме выборки внешний конденсатор Cext подключается к внутреннему, и внутренний заряд распределяется между обоими конденсаторами. Напряжение (без учета того, что уже есть на Cext, посчитаем выброс при выборке) будет рассчитываться так: Uh * Csh = Us * (Csh + Cext) Us = Uh * (Csh / Csh + Cext) Чем больше внешний конденсатор, тем меньший выброс на входе АЦП будет при переключении в режим выборки. Резистор Rin в расчете выброса не участвует. Он определяет наклон, с которым выброс спадает. Чем меньше резистор, тем короче выброс, согласно постоянной времени Rin * (Csh + Cext).
|
|
|
|
|
Mar 3 2014, 21:54
|

Местный
  
Группа: Участник
Сообщений: 318
Регистрация: 21-07-06
Из: Минск
Пользователь №: 18 986

|
Цитата(ViKo @ Mar 3 2014, 20:46)  Чем больше внешний конденсатор, тем меньший выброс на входе АЦП будет при переключении в режим выборки. Я говорил про случай, когда Cext >> Csh и выброс не превышает 1/2 LSB. Т.е. по причине выброса ошибки нет вообще. Но, тем не менее, ошибка появляется, если Rin > Vlsb / (2 * Vref * Csh * Fs). И эта ошибка не зависит от Cext, а только от Rin и Fs. Скажем, при частоте выборок 1 кГц ошибка начнет появляться при увеличении Rin выше 15 кОм. И никаким увеличением емкости на входе АЦП ее не устранить.
Сообщение отредактировал Леонид Иванович - Mar 4 2014, 09:52
--------------------
|
|
|
|
|
Mar 4 2014, 08:03
|

Универсальный солдатик
     
Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362

|
Если от Cext не зависит, то почему вы назвали совет повесить дополнительный конденсатор "вредным"? Если нет выброса, откуда возьмется ошибка? В ваших формулах фигурирует Fs. Напоминаю еще раз, что ток идет только во время выборки. Во время преобразования тока нет. А источник заряжает внешний конденсатор постоянно. Ваша формула годится для постоянного тока, заряжающего (разряжающего) внутренний конденсатор. В данном случае это не так. Цитата(Леонид Иванович @ Mar 4 2014, 00:54)  Скажем, при частоте выборок 1 кГц ошибка начнет появляться при увеличении Rin выше 8 кОм. Можете показать на спайс-модели?
|
|
|
|
|
Mar 4 2014, 09:02
|

Местный
  
Группа: Участник
Сообщений: 318
Регистрация: 21-07-06
Из: Минск
Пользователь №: 18 986

|
Цитата(ViKo @ Mar 4 2014, 11:03)  Если от Cext не зависит, то почему вы назвали совет повесить дополнительный конденсатор "вредным"? Потому что Вы невнимательно читали то, что я написал. Возможны два случая, когда ошибка будет отсутсвовать: это или маленькая емкость Cext (в пределе - только емкость УВХ), которая успевает заряжаться с точностью лучше 1/2 LSB за время выборки, или большая емкость Cext, которая за время выборки разряжается менее чем на 1/2 LSB. В первом случае на величину ошибки влияет значение RC и время выборки, период выборок значения не имеет. Во втором случае имеет значение период выборок и величина R, время выборки значения не имеет. "Вредным" Cext может оказаться в первом случае, его добавление может привести к появлению заметной ошибки. Цитата(ViKo @ Mar 4 2014, 11:03)  Если нет выброса, откуда возьмется ошибка? Уф, который раз уже... Ошибка возмется из-за среднего входного тока АЦП. Во время каждой выборки через входной пин АЦП проходит некий заряд. Если этот заряд умножить на частоту выборок, получим средний входной ток. Цитата(ViKo @ Mar 4 2014, 11:03)  В ваших формулах фигурирует Fs. Напоминаю еще раз, что ток идет только во время выборки. Во время преобразования тока нет. А источник заряжает внешний конденсатор постоянно. Так и есть. Между Cext и Csh течет импульсный ток, а между источником сигнала и Cext - практически постоянный. Вот этот ток и создает падение на Rin, что приводит к ошибке. Цитата(ViKo @ Mar 4 2014, 11:03)  Ваша формула годится для постоянного тока, заряжающего (разряжающего) внутренний конденсатор. В данном случае это не так. Моя формула для среднего входного тока, который по переносу заряда в единицу времени соответствует импульсному входному току АЦП. Цитата(ViKo @ Mar 4 2014, 11:03)  Можете показать на спайс-модели? Легко. И на модели, и вживую на плате с STM32. Вот скриншот результатов моделирования, схему модели приводил у себя в LJ.
Сообщение отредактировал Леонид Иванович - Mar 4 2014, 09:04
Эскизы прикрепленных изображений
--------------------
|
|
|
|
|
Mar 4 2014, 11:25
|

Местный
  
Группа: Участник
Сообщений: 318
Регистрация: 21-07-06
Из: Минск
Пользователь №: 18 986

|
Вообще, выводы находятся в соответствии с рекомендациями документа AN2834. Там на стр. 40 приведена точная формула для минимального периода выборок tc (величина, обратная Fs) для случая большой Cext. Только там может сбить с толку фраза "An extra large Cext enables sampling more often". Формула в документе приведена верная, вот только не сказано, что при увеличении Cext величина Fs не может быть сделана сколь угодно большой, так как она стремится к своему пределу, который дает приведенная мной формула.
Поэтому если источник сигнала обладает высоким внутренним сопротивлением Rin, то на вход АЦП нужно подключить большую емкость Cext > Csh * 2^(N+1) (для АЦП STM32F100 получается Cext > 68 нФ) и установить частоту выборок не более предельного значения Fs < 1 / (2^(N+1) * Csh * Rin). Для АЦП STM32F100 получается Fs < 15*10^6 / Rin. Например, для Rin = 100 кОм частота выборок не должна превышать 150 Гц.
Для случая низкоимпедансного источника сигнала (например, выход ОУ), тоже рекомендуется на вход АЦП утанавливать RC-цепочку. Ее назначение - изолировать выход ОУ от входа АЦП с его большими импульсными токами в момент начала выборки. Только в этом случае емкость выбирается значительно меньшей. Рекомендуют порядка 20..50 * Csh, для STM32F100 это около 220..470 пФ. Для получения ошибки меньше 1/2 LSB постоянная времени входной RC-цепочки должна быть в ln(2^(N+1)) раз (для случая 12-разрядного АЦП примерно в 9 раз) меньше времени выборки ts.
Сообщение отредактировал Леонид Иванович - Mar 4 2014, 11:46
--------------------
|
|
|
|
|
  |
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|