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

 
 
> SAM4S, Ничего не выходит
Грендайзер
сообщение Oct 14 2014, 18:01
Сообщение #1


Местный
***

Группа: Участник
Сообщений: 368
Регистрация: 18-04-11
Из: Город-герой Москва
Пользователь №: 64 451



Здравствуйте всем! Попала в руки отлпдочная плата SAM4S-EK2 на базе контроллера ATSAM4SD32C. Ранее никогда не работал ни с ARM ни с Cortex ну и встрял. Немного работал с AVR так там всё элементарно... Надо что то - посмотрел в даташите необходимый регистр, записал в него что нужно и всё... А здесь.. смотрел в даташит, так там как будто Лев Толстой приложился столько букв sad.gif И хоть убей, не вижу как элементарно вывести единичку в порт?

Сообщение отредактировал Грендайзер - Oct 14 2014, 18:08
Go to the top of the page
 
+Quote Post
5 страниц V  < 1 2 3 4 > »   
Start new topic
Ответов (15 - 29)
Golikov A.
сообщение Oct 15 2014, 12:50
Сообщение #16


Гуру
******

Группа: Свой
Сообщений: 4 256
Регистрация: 17-02-06
Пользователь №: 14 454



а я бы сказал что так делать не надо, по описанной выше причине. Не надо делать своих дефайнов к ногам. Свои дефайны могу быть из раздела
DIAGNOSTIC_LED_ON, DIAGNOSTIC_LED_OFF, за которыми скрыть работу с ножкой порта, но через стандартные дефайны из заголовочного файла. ИМХО конечно...


Цитата
, т.к. обращение напрямую к регистрам конечно не самый красивый способ

не соглашусь. Это самый прямой и быстрый способ. Если не брать чужую библиотеку, надо писать свою, где функции настройки просто имеют внутри прямой доступ к регистрам. Это самый короткий, прямой путь без сюрпризов. Почему он не красив?
Go to the top of the page
 
+Quote Post
Leopoldius
сообщение Oct 15 2014, 13:00
Сообщение #17


Частый гость
**

Группа: Свой
Сообщений: 78
Регистрация: 23-03-11
Из: Россия
Пользователь №: 63 824



Цитата(Golikov A. @ Oct 15 2014, 15:50) *
а я бы сказал что так делать не надо, по описанной выше причине. Не надо делать своих дефайнов к ногам.


Да дело же не в дефайнах - это идеология ASF от Атмела. А так, да - стоит использовать только дефайны для удобства чтения и создания переносимости.

А по поводу скорости работы, кто же спорит. Напрямую всегда быстрее, чем окольными путями(ASF, STD Periph Lib и т.д, правда все зависит от реализации этих библиотек)
Go to the top of the page
 
+Quote Post
KnightIgor
сообщение Oct 15 2014, 13:03
Сообщение #18


Знающий
****

Группа: Участник
Сообщений: 643
Регистрация: 29-05-09
Из: Германия
Пользователь №: 49 725



Цитата(Грендайзер @ Oct 15 2014, 13:55) *
KnightIgor, спасибо, CMSIS обязательно изучу, т.к. обращение напрямую к регистрам конечно не самый красивый способ. Впрочем и работа с набором непонятных ф-ций то же не особо доставляет.

Всегда пожалуйста, но мне кажется, Вы не совсем поняли: CMSIS не исключает обращения к регистрам напрямую. Она даже поощряет это, но вводит некоторые правила наименования тех самых регистров и битов в них, а также принцип доступа к периферийным регистрам как к полям некой структуры. Самих функций в CMSIS немного и касаются они только ядра и базовой периферии, то есть NVIC (контроллера прерываний), SYSTICK (генератора системных тиков) и некоторых других основ. Вам нужно, - и прислушайтесь к этому совету, - сначала изучить и применить периферийную библиотеку для Вашего процессора. Это надстройка над регистрами. Пусть многие ругают такие библиотеки и их индусских воплотителей, но они очень помогают для быстрого старта, потому что имеют сами за себя говорящие имена функций и параметры, скрывающие внутреннюю суть тех самых регистров и битов. И кстати, не все такие библиотеки плохи: для EFM32 они просто замечательны.
Go to the top of the page
 
+Quote Post
Грендайзер
сообщение Oct 15 2014, 13:39
Сообщение #19


Местный
***

Группа: Участник
Сообщений: 368
Регистрация: 18-04-11
Из: Город-герой Москва
Пользователь №: 64 451



Цитата
Это самый короткий, прямой путь без сюрпризов. Почему он не красив?

А действительно, почему?! Наверное Вы правы!!! В конечном итоге можно будет процесс программирования сделать немного похожим на программирование тех же АВР cool.gif
Цитата
А по поводу скорости работы, кто же спорит. Напрямую всегда быстрее, чем окольными путями(ASF, STD Periph Lib и т.д, правда все зависит от реализации этих библиотек)

А вот этот момент мне критичен. Вообще работаю с ПЛИС поэтому всегда знаю, сколько тактов у меня на что уходит, и если такого понимания нет чувствую себя немного не уютно. Но создавать свои проекты с учётом временных особенностей кристалла крайне сложно и долго, поэтому, и решил где возможно использовать готовые решения (например тот же Nios), облегчает жизь, но не стоимость изделия. Так что чёткое понимание это есть хорошо, правда в этом случае, придётся перейти на ассемблер, но это уже черезчур. Времени конечно нет, но его никогда нет. Тут советывался с одним коллегой, он работает с ядром ARM где то пол года, говорит что даже не стал вникать в эти ф-ции. Начал сразу писать свои библиотеки (впрочем у него огромный опыт работы с АВР и чего он там для них токо не писал).

Сообщение отредактировал Грендайзер - Oct 15 2014, 13:43
Go to the top of the page
 
+Quote Post
Golikov A.
сообщение Oct 15 2014, 14:17
Сообщение #20


Гуру
******

Группа: Свой
Сообщений: 4 256
Регистрация: 17-02-06
Пользователь №: 14 454



Правда как всегда по середине.
Я всегда за то что нельзя использовать чужой код без проверки. Есть люди что верят библиотекам и даже не сморят что там внутри, а бывает всякое. Отрицать библиотеки тоже не правильно, часто они ускоряют процесс и делают код удобным для совместной работы, легче вникать что там понаделано.

Претензии у меня к ним такие. Библиотеки часто грешат, особенно те функции что настраивают сложную периферию тем что считают процессор в состоянии после ресета. А если есть бутлоадер и там уже что-то настроено? Пару раз так обсерался, не проверил и получил гемор и отладку...

А вот число тактов на команду - это суровый момент, процы имеют и схемы пред выбора команд, и конвейер и прерывания, и контроллер прерываний, не всегда у вас получится уследить за числом тактов%) да и компилятор помогает. А вот от Ассемблера я бы вас предостерег, мне кажется уже не того уровня техника. Только ассемблерные вставки в критических секциях не более, а то слишком дорого будет обслуживать проект.

Хотя все изложенное ИМХО
Go to the top of the page
 
+Quote Post
Грендайзер
сообщение Jul 29 2015, 09:54
Сообщение #21


Местный
***

Группа: Участник
Сообщений: 368
Регистрация: 18-04-11
Из: Город-герой Москва
Пользователь №: 64 451



Здравствуйте! Продолжаю мучить ATSAM4S32C. Дошёл до ЦАП и возникло 2 вопроса.
1) В электрических параметрах на встроенный ЦАП указан параметр Startup Time - что это?
2) В этих же электрических данных указано, что максимальная тактовая частота ЦАП составляет 50МГц. Но максимальная частота ядра достигает 120МГц. Частота ядра, как собственно и переферии есть Master Clock (MCK) которая ирёт с контроллера управления питанием Power Management Controller (PMC). В описаниии на ЦАП указано: The DACC uses the master clock (MCK) divided by two to perform conversions. Т.о. если я правильно понимаю, либо частота ядра не должна превышать 100МГц (что на 20МГц ниже чем максимальная) либо отказаться от использования встроенного ЦАП? blink.gif С АЦП у меня такой проблемы не возникло, т.к. тот имеет свой собственный делитель частоты. Но вот в ЦАПе я такого не обнаружл sad.gif Как быть? Что делать? Кто виноват?
Go to the top of the page
 
+Quote Post
Obam
сообщение Jul 29 2015, 10:13
Сообщение #22


Знающий
****

Группа: Участник
Сообщений: 756
Регистрация: 14-11-14
Пользователь №: 83 663



Формально да (но попробовать не запрещено), ЦАП быстрее 50 МГц тактировать нельзя; разница 100 и 120 МГц для тактирования ядра не особо заметна, т.к. память программ работает с 6 WS циклами.

Сообщение отредактировал Obam - Jul 29 2015, 10:14


--------------------
Пролетарий умственного труда.
Go to the top of the page
 
+Quote Post
Грендайзер
сообщение Jul 29 2015, 10:17
Сообщение #23


Местный
***

Группа: Участник
Сообщений: 368
Регистрация: 18-04-11
Из: Город-герой Москва
Пользователь №: 64 451



Всё ясно, спасибо. Хотя всёравно как то печальноsad.gif
Go to the top of the page
 
+Quote Post
Грендайзер
сообщение Aug 5 2015, 10:10
Сообщение #24


Местный
***

Группа: Участник
Сообщений: 368
Регистрация: 18-04-11
Из: Город-герой Москва
Пользователь №: 64 451



Всем доброго времени суток. Опять столкнулся с проблемой, точнее с двумя. Первое - никак не могу победить оптимизатор в AtmelStudio. Это сволочь помоиму мне палки в колёса тычит. А именно:
написал программку которая принимает данные с АЦП, пропускает через ФВЧ и кладёт в ЦАП.
CODE
#include "sam.h"
int din = 0;
int dout = 0;
int dacc_in = 0;
int din_1 = 0;
volatile int flag = 0;

int main(void)
{

SystemInit();
//--------------- Включение глобальных прерываний -----------------------------
__enable_irq ();

//--------------- Enable Interrupts in NVIC ----------------------------
NVIC_EnableIRQ(DACC_IRQn);
NVIC_EnableIRQ(ADC_IRQn);
//--------------- Приоритет прерывания ЦАП ниже чем у АЦП
NVIC_SetPriority (DACC_IRQn, 2);
//----------- далее настройка переферии------------------------
.
.
.
//----------------------------------------------------------------------
int main(void)
{
switch(flag)
{
case 0: // если прерывание от АЦП не произошло, моргать светодиодами
{
{PIOA -> PIO_CODR = PIO_CODR_P19 | PIO_CODR_P20;}
for (int i = 0; i < 1000000; i ++){}
{PIOA -> PIO_SODR = PIO_SODR_P19 | PIO_SODR_P20;}
for (int i = 0; i < 1000000; i ++){}
break;
}
case 1: // Если прерывание от АЦП было - гнать данные через ФВЧ
{
dacc_in = dout + din - din_1;
dout = dacc_in * 0.9 + 600;
din_1 = din;
break;
}
default : {break;}
}
return 0;
}

\\ Подпрограммы прерываний
\\------------ АЦП----------------
void ADC_Handler( void )
{
volatile int IRQ_sense = 0;
IRQ_sense = ADC -> ADC_ISR & (ADC_IER_EOCAL | ADC_IER_EOC5);

switch(IRQ_sense)
{
case ADC_IER_EOCAL : // автокалибровка АЦП
{
{PIOA -> PIO_CODR = PIO_CODR_P19 | PIO_CODR_P20;}
{PIOA -> PIO_SODR = PIO_SODR_P19 | PIO_SODR_P20;}
ADC -> ADC_IER = ADC_IER_EOC5;
ADC -> ADC_CR = ADC_CR_START;
return;
}

case ADC_IER_EOC5 :
{
flag = 1; // Говорим что было прерывание от АЦП
din = ADC -> ADC_CDR[5] & ADC_CDR_DATA_Msk; // Данные с АЦП
ADC -> ADC_CR = ADC_CR_START; // Вновь запускаем АЦП
return;
}

default : {return;}
}
}

//-------------------------- ЦАП --------------------------------
void DACC_Handler( void )
{
volatile int IRQ_sense = 0;
IRQ_sense = DACC -> DACC_ISR;// & (DACC_ISR_EOC);
DACC -> DACC_CDR = DACC_CDR_DATA(dout);
return;
}


Так вот у меня программа лишь могргает светодиодами... Тупо.. В пошаговой отладке оказывается, что din меняет свое значение, а вот dout просто проскакивается, процессор его не замечая выполнят команду flag = 0 и всё. При этом если формулу фильтра вписать в функцию прерывания от АЦП то всё работает. В чём дело? angry.gif

Сообщение отредактировал IgorKossak - Aug 5 2015, 19:37
Причина редактирования: [codebox] для длинного кода, [code] - для короткого!
Go to the top of the page
 
+Quote Post
Obam
сообщение Aug 5 2015, 11:04
Сообщение #25


Знающий
****

Группа: Участник
Сообщений: 756
Регистрация: 14-11-14
Пользователь №: 83 663



Не грех посмотреть в сгенерённый код: куда dout там делся… sm.gif
А вообще, "volatile" не только для flag…


--------------------
Пролетарий умственного труда.
Go to the top of the page
 
+Quote Post
Грендайзер
сообщение Aug 5 2015, 11:56
Сообщение #26


Местный
***

Группа: Участник
Сообщений: 368
Регистрация: 18-04-11
Из: Город-герой Москва
Пользователь №: 64 451



Цитата
Не грех посмотреть в сгенерённый код: куда dout там делся…
А кто ж его знает... оптимизировался б... angry.gif Приведу кусочек дизассемблированного кода на рисуночке.
P.S.
Попробовал везде volatile напихать... амплитуда на выходе ЦАПа уменьшилась почти в 10 раз по сравнению с тем, что без волатиле, при том осциллограма сильно дёргается... Вообщем жесть какая то...

Сообщение отредактировал Грендайзер - Aug 5 2015, 11:57
Эскизы прикрепленных изображений
Прикрепленное изображение
 
Go to the top of the page
 
+Quote Post
scifi
сообщение Aug 5 2015, 12:13
Сообщение #27


Гуру
******

Группа: Свой
Сообщений: 3 020
Регистрация: 7-02-07
Пользователь №: 25 136



У вас шнурки развязались не код, а полный бардак. Два раза написано "int main(void)", отсутствует строчка "flag = 0;", хоть вы на неё и ссылаетесь, и вообще выглядит как какая-то лапша.
С таким бардаком неудивительно, что ничто не работает.
А бездумное добавление volatile где попало - это танцы с бубном.
Go to the top of the page
 
+Quote Post
Грендайзер
сообщение Aug 5 2015, 12:40
Сообщение #28


Местный
***

Группа: Участник
Сообщений: 368
Регистрация: 18-04-11
Из: Город-герой Москва
Пользователь №: 64 451



прошу прощения за ошибки допущенные при копировании. вот поправленный вариант
CODE
#include "sam.h"

int din = 0;
int dout = 0;
int dacc_in = 0;
int din_1 = 0;
volatile int flag = 0;

int main(void)
{

SystemInit();
//--------------- Enable Global Interrupts -----------------------------
__enable_irq ();

//--------------- Enable Interrupts in NVIC ----------------------------
NVIC_EnableIRQ(DACC_IRQn);
NVIC_EnableIRQ(ADC_IRQn);

NVIC_SetPriority (DACC_IRQn, 2);

while (1)
{
switch(flag)
{
case 0:// если прерывание от АЦП не произошло, моргать светодиодами
{
{PIOA -> PIO_CODR = PIO_CODR_P19 | PIO_CODR_P20;}
for (int i = 0; i < 1000000; i ++){}
{PIOA -> PIO_SODR = PIO_SODR_P19 | PIO_SODR_P20;}
for (int i = 0; i < 1000000; i ++){}
break;
}
case 1: // Если прерывание от АЦП было - гнать данные через ФВЧ
{
dacc_in = dout + din - din_1;
dout = dacc_in * 0.9 + 600;
din_1 = din;
flag = 0;
break;
}
default : {break;}
}
}
return 0;
}

\\ Подпрограммы прерываний
\\------------ АЦП----------------
void ADC_Handler( void )
{
volatile int IRQ_sense = 0;
IRQ_sense = ADC -> ADC_ISR & (ADC_IER_EOCAL | ADC_IER_EOC5);

switch(IRQ_sense)
{
case ADC_IER_EOCAL : // автокалибровка АЦП
{
{PIOA -> PIO_CODR = PIO_CODR_P19 | PIO_CODR_P20;}
{PIOA -> PIO_SODR = PIO_SODR_P19 | PIO_SODR_P20;}
ADC -> ADC_IER = ADC_IER_EOC5;
ADC -> ADC_CR = ADC_CR_START;
return;
}

case ADC_IER_EOC5 :
{
flag = 1; // Говорим что было прерывание от АЦП
din = ADC -> ADC_CDR[5] & ADC_CDR_DATA_Msk;
ADC -> ADC_CR = ADC_CR_START;
return;
}

default : {return;}
}
}

//-------------------------- ЦАП --------------------------------
void DACC_Handler( void )
{
volatile int IRQ_sense = 0;
IRQ_sense = DACC -> DACC_ISR;
DACC -> DACC_CDR = DACC_CDR_DATA(dout);
return;

}

P.S.
Процесс настройки переферии указывать не стал

Сообщение отредактировал IgorKossak - Aug 5 2015, 19:37
Причина редактирования: [codebox] для длинного кода, [code] - для короткого!
Go to the top of the page
 
+Quote Post
Golikov A.
сообщение Aug 5 2015, 12:55
Сообщение #29


Гуру
******

Группа: Свой
Сообщений: 4 256
Регистрация: 17-02-06
Пользователь №: 14 454



int din = 0;
int dout = 0;

вот это под volatile

потом смотрим на

dacc_in = dout + din - din_1;
dout = dacc_in * 0.9 + 600;
din_1 = din;

допустим din не меняется,
dacc_in = dout;
dout = dac_in * 0.9 + 600 => dout = dout*0.9 + 600;

какая там у вас битность ЦАП? не переполнится ли он таким макаром?

Прерывания кстати где сбрасываются?
Go to the top of the page
 
+Quote Post
Грендайзер
сообщение Aug 5 2015, 13:14
Сообщение #30


Местный
***

Группа: Участник
Сообщений: 368
Регистрация: 18-04-11
Из: Город-герой Москва
Пользователь №: 64 451



Цитата
какая там у вас битность ЦАП? не переполнится ли он таким макаром?

12 бит. Нет, не переполнится. Как я уже писал, всё работает если данный кусок кода поместить в ф-цию обработчика прерываний.
Цитата
Прерывания кстати где сбрасываются?

В смысле? Прерывания срабатывают следующим образом
1) В процессе настройки переферии запускается ЦАП;
2) Когда завершается автокалибровка;
3) После автокалибровки запускается ЦАП;
Все прерывания отрабатывают. И ещё пробовал отключать оптимизацию, код выполнялся правильно, но работал оооочень медленно.
Go to the top of the page
 
+Quote Post

5 страниц V  < 1 2 3 4 > » 
Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


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


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