Jump to content

    
Sign in to follow this  
Vlad_G

Просмотр переменных в STMStudio

Recommended Posts

День добрый!

Пытаюсь импортировать переменные в студию (картинка 1).

Выбираю файл elf - пишет, что ошибка адресов в таблице... (картинка 2).

Жму - ОК и ... фигня какая-то (картинка 3). Ни одной моей переменной нет.

Что не так делаю, понять не могу? В интернетах вроде все просто на эту тему: делай раз, делай два. Скрины подтверждают.

Что имею: STLink/V2, "беленькай такой, квадратно-овальненький", вроде как фирменный, не с али. Atollic TrueSTUDIO for STM32 9.0.1. STM32F030F4. Программирую через STM32 ST-LINK Utility. Программа работает, дебаг в атоллике запускается.

Пытался проект сделать в System Workbench for STM32 - результат тот же.

 

 

1.jpg

2.jpg

3.jpg

Edited by Vlad_G

Share this post


Link to post
Share on other sites

Сделаю небольшой ап.

Видимо никто не использует STMStudio, либо вопрос уж совсем глупый ... 

Проблема решена. Надо было объявить переменные как глобальные и еще, до кучи, объявить их как волатильные. После этого все работает. В немногочисленных статьях на тему - как работать в STMStudio во фрагментах кода переменные были локальными и не волатильными. И как все это реально работало оставим на совести авторов. Но правда и камни у них были другие.

На счет камней. Дали мне тут F103, загнал в него тот же проект и получилось следующее: переменную надо также объявлять как глобальную, но волатилить ее уже не обязательно, отладка работает и без этого уточнения. А если взять F4хх, как в тырнетовских статьях, то переменные, возможно, могут так и остаться локальными. И еще с F103 не выскакивает окошко с предупреждением как на второй картинке. Получается полный зоопарк... И как можно хаить микрочип после этого? 

 

Edited by Vlad_G

Share this post


Link to post
Share on other sites
3 часа назад, Vlad_G сказал:

Надо было объявить переменные как глобальные и еще, до кучи, объявить их как волатильные

"То к темю их прижмет, то их на хвост нанижет,
То их понюхает, то их полижет;
Очки не действуют никак."

3 часа назад, Vlad_G сказал:

И как можно хаить микрочип после этого? 

"К несчастью, то ж бывает у людей:
Как ни полезна вещь, — цены не зная ей,
Невежда про нее свой толк все к худу клонит;
А ежели невежда познатней,
Так он ее еще и гонит."

Share this post


Link to post
Share on other sites
2 hours ago, Vlad_G said:

Надо было объявить переменные как глобальные и еще, до кучи, объявить их как волатильные.

volatile для STMStudio точно не нужно. Скорее всего просто оптимизация выкинула ваши переменные за ненадобностью.

Share this post


Link to post
Share on other sites
1 hour ago, alex2103 said:

оптимизация выкинула ваши переменные за ненадобностью.

Сама программа работала как надо, по осциллографу видно было, те оптимизация не выкинула лишнего. Не мог вытащить значение переменной в Студию. Ну а объявление valatile - это уже просто методом тыка. Что теряю, если попробую?

Share this post


Link to post
Share on other sites
33 minutes ago, Vlad_G said:

И еще с F103 не выскакивает окошко с предупреждением как на второй картинке

Поискать APBPrescTable в исходниках - не пробовали? Помнится мне, это в HAL'е массив для пересчёта делителя для шины APB (в человеческих /1 /2 и т.д.) в значение регистра прескалера. Есть ли оно в HAL'е от 32F030 - понятия не имею.

Зачем оно прибито гвоздями к этой студии, вопрос риторический.

 

Ну и в зависимость от камня я не верю. Вот в зависимость от типа переменной (глобальная-локальная) и в зависимость от степени оптимизации компилятора - очень даже.

Share this post


Link to post
Share on other sites

Ну в общем то зачем в этой студии локальные переменные? Обычно задача какой-то лог снять или график в риалтайме наглядно посмотреть. 

Если надо прям внутри функций копаться, то STMStudio мне кажется не для этого. Для этого есть отладчики.

6 hours ago, Vlad_G said:

Сама программа работала как надо, по осциллографу видно было, те оптимизация не выкинула лишнего.

Странно было бы если после оптимизации оно работало как-то совсем не так. Без кода трудно сказать что могло получится из вашего кода после оптимизации. 

По поводу ошибок что он не может найти какие-то переменные - я их тоже видел на f205, f407. Но работать это не мешало и я не стал выяснять где оно там гвоздями прибито.

Share this post


Link to post
Share on other sites
1 hour ago, alex2103 said:

Без кода трудно сказать что могло получится из вашего кода после оптимизации. 

Код не секрет:

 /* USER CODE BEGIN Includes */

	  uint32_t adc_res_0, adc_res_7;
	  uint32_t adc_res, count;
	  uint32_t pwm_out = 500;					//Начальная длительность шим

/* USER CODE END Includes */





/* USER CODE BEGIN 3 */

	  //Настройка ШИМ **********
	  //
	  TIM14->PSC = 0;							//предделитель: =0 деление на 1, =1 деление на 2
	  TIM14->ARR = 2047;						//период шим Fsys/период (48МГц/2047=23,44 кГц)
	  TIM14->CCR1 = pwm_out;					//длительность импульса, должно быть <= период шим

	  TIM14->CCER |= TIM_CCER_CC1E;				//канал1 как выход
	  TIM14->CR1 |= TIM_CR1_CEN;				//включаем шим

	  //Настройка АЦП **********
	  ADC1->CR &= ~(ADC_CR_ADEN); 				//остановили АЦП для калибровки
	  ADC1->CFGR1 &= ~(ADC_CFGR1_DMAEN);		//отключили доступ ДМА к АЦП
	  ADC1->CR |= ADC_CR_ADCAL; 				//запуск калибровки АЦП
	  while (ADC1->CR & ADC_CR_ADCAL); 			//ожидаем окончания калибровки

	  if ((ADC1->ISR & ADC_ISR_ADRDY) != 0)		//включаем АЦП
	  	  {
	      	  ADC1->ISR |= ADC_ISR_ADRDY;
	      }
	      	ADC1->CR |= ADC_CR_ADEN;			//включили АЦП
	      	while ((ADC1->ISR & ADC_ISR_ADRDY) == 0)
	  //Завершили настройки**********


	  //Делаем измерения. Рабочий цикл.
	  while(1)
	  	  {
//_label_1:
	      	  adc_res_0 = 0;
	      	  adc_res_7 = 0;

	      	  ADC1 -> CHSELR = 1;							//выбрали канал IN0
	      	  for (count = 0; count < 8; count++)			//усредняем по 8-ми измерениям
	      	  	  {
	      	  		ADC1->ISR |= ADC_ISR_EOS;				//очистили флаг окончания преобразования
	      	  		ADC1->CR |= ADC_CR_ADSTART;				//запуск преобразования
	      	  		while ((ADC1->ISR & ADC_ISR_EOS) == 0); //ожидаем окончания преобразования
	      	  		adc_res_0 = adc_res_0 + ADC1->DR;		//суммируем результат
	      	  	  }
	      	  adc_res_0 = adc_res_0 >> 3;					//усреднили
	      	  adc_res_0 = adc_res_0 / 2;

	      	  ADC1 -> CHSELR = 128;							//выбрали канал IN7
	      	  for (count = 0; count < 8; count++)			//усредняем по 8-ми измерениям
	      	  	  {
	      	  		ADC1->ISR |= ADC_ISR_EOS;				//очистили флаг окончания преобразования
	      	  		ADC1->CR |= ADC_CR_ADSTART;				//запуск преобразования
	      	  		while ((ADC1->ISR & ADC_ISR_EOS) == 0); //ожидаем окончания преобразования
	      	  		adc_res_7 = adc_res_7 + ADC1->DR;		//читаем результат
	      	  	  }
	      	  adc_res_7 = adc_res_7 >> 3;					//усреднили
	      	  adc_res_7 = adc_res_7 / 2;
	      	  //**********

	      	  adc_res = ((adc_res_7 * 193) / (adc_res_0 + 488)) + 1250;

	      	  pwm_out = adc_res;
  
	      	  TIM14->CCR1 = pwm_out;

	  	  }

  }
  /* USER CODE END 3 */

Хм. В окне редактирования кода все красивше было....

Проект сгенерил кубом, для начинающего самое то, а то ломай потом голову где-что пропустил. Алгоритм простой, измеряем два напряжения, делим одно на другое и записываем в шим.

Простенький, учебно-тренировочный проектик, stm можно сказать только в руки взял. /* USER CODE BEGIN 3 */ - внутри - main(), переменные вне. Изначально были внутри main().

Здесь переменные как volatile не описаны, промежуточный вариант, не стал в посте исправлять, но без этого значение переменной в студии всегда - ноль, на F030F4. На F103 показывает вполне адекватные значения (не придумываю, что вижу о том и пою ) ). В общем-то Студия меня устроила, как достаточно простой инструмент. Добавить пару кнопок на МК, чтоб можно было выходить из точек останова для корректного просмотра в Студии, а то она пропускает некоторые моменты времени и показывает уже значение опосля, а не тогда, когда надо. Еще б понять кто косячит - я или Студия...

Share this post


Link to post
Share on other sites

Во-первых я полагаю, что этот код работает не так, как вы хотели. Или работает как вы хотели чисто случайно, ибо цикл whle(1) находится внутри while ((ADC1->ISR & ADC_ISR_ADRDY) == 0)

Во-вторых, любой вменяемый компилятор с включенной оптимизацией разместит ваши переменные в регистрах, но не все отладчики, к сожалению, умеют отслеживать переменные в регистрах. Еще сложнее, когда переменная "скачет" из регистра на стек и обратно. Поэтому в таких случаях имеет смысл пройтись по шагам дизассемблированный текст проблемного куска и понять, где в данный момент находится переменная.

Разное поведение отладчика с разными процессорами объясняется либо разными настройками оптимизации, либо немного разным кодом для ядер M0 и M3. Да и АЦП у 030 и 103 сильно разные, так что и исходный код ваш должен был сильно отличаться.

В-третьих: не знаю вашей задачи, но логика подсказывает, что для повышения точности надо измерять не 8 отсчетов одного канала и 8 отсчетов второго, а восемь раз измерить оба канала. И на STM32 такое измерение можно сделать при помощи АЦП в связке с ПДП вообще без вмешательства ядра.

Share this post


Link to post
Share on other sites
22 hours ago, Vlad_G said:

while ((ADC1->ISR & ADC_ISR_ADRDY) == 0)

Не хватает точки запятой в конце. Или пустого блока из фигурных скобок. И не понятно, почему компилятор на это не ругается.

Share this post


Link to post
Share on other sites
41 минуту назад, Darth Vader сказал:

И не понятно, почему компилятор на это не ругается.

Непонятно, что вам не понятно - это абсолютно законная конструкция, телом является следующий while(1)

Share this post


Link to post
Share on other sites

Да, действительно в конструкции:

((ADC1->ISR & ADC_ISR_ADRDY) == 0)

Не поставил - ; Везде поставил, а тут пропустил. Но компилятор и не пикнул. Исправил. Но на работу программы это не повлияло, по крайней мере на поверхностный взгляд. Видимо случайностей полно в жизни.

Спрошу еще, чтоб не постить новую тему.

Сгенерил кубом новый проектик, мк все тот же, шим на порту PB1 - TIM14_CH1, все настройки частоты, длительности ввел в кубе. Дальше хочу запустить все это в работу, для этого в кубовую генерацию вношу две строчки:

/* USER CODE BEGIN 2 */
  	  
  	  TIM14->CCER |= TIM_CCER_CC1E;				//канал1 как выход
  	  TIM14->CR1 |= TIM_CR1_CEN;				//включаем шим

  /* USER CODE END 2 */

  /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  while (1)
  {

  /* USER CODE END WHILE */

  /* USER CODE BEGIN 3 */

  }
  /* USER CODE END 3 */

все работает согласно настроек. Теперь хочу использовать HAL  для запуска шима. Вместо этих строк набираю - HAL_TIM_PWM_Start(TIM14, TIM_CHANNEL_1); Компилятор не ругается, но и шим не работает...

На странице 496 HAL_F0.pdf  описание функции HAL_TIM_PWM_Start. Покурил интернет, нашел: HAL_TIM_PWM_Start(&htim14, TIM_CHANNEL_1); При такой записи все заработало. Вот скажите - откуда взялось &htim14 ? Где искать? htim есть, про 14 догадаться можно, & откуда? А то описание HAL на 1300 листов, функций много и где, что искать хз. На все случаи не напостишься.

ЗЫ. Прошу сильно не пинать, если кажется, что полная безнадёга.

Share this post


Link to post
Share on other sites
58 minutes ago, Vlad_G said:

& откуда?

Функция HAL_TIM_PWM_Start  примает на вход *указатель на хендл, переменная htim это хендл(структура), так как функция принимает указатель амперсанд позволяет взять адрес данной переменной, это можно прочесть в любой книге по С. Или в гугл:  "С указатели"

 

1 hour ago, Vlad_G said:

Вот скажите - откуда взялось &htim14 ? Где искать? htim есть, про 14 догадаться можно

Вы благодаря CubeMx сгенерили пример работы с таймером, вот и смотрите какой хендл CubeMx создал в шапке файла. Там мог быть htim2 и/либо htim14 в вашем случае просто htim.

И нужно помнить, что CubeMx это просто удобный инструмент в возможность которого входит просто сгенерить пример работы с выбранной периферией! не нужно думать что он за вас сделает весь проект, а после, поняв это негативно отзываться о приложении. Кроме того ST'шники предоставляют свои либы под названием HAL и LL для работы с контроллерами(впрочем, как и все производители мк) но первые версии были довольно сырые, и по какой-то причине слава сырых библиотек перетекла на CubeMx и сегодня, как было сказано выше, многие мартышки просто гонят на бедолагу CubeMx.

 

Share this post


Link to post
Share on other sites

Спасибо!

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

А вот нагнать волну на эффективных менеджеров можно - недобрыйдядя объяснил им, что stm на семь копеек дешевле чем восьмибитники, а круче аж на целый червонец. И то, что в ацп отсутствует верхний и нижний рефренсы (или хотя б можно подключить из вне) уже по фиг. Многоногие stm-ы не особо лезут по габаритам. Я не против прогресса, просто каждой задаче своя комплектация. Ладно, это уже в философский раздел.

Благодарю за помощь! И за то, что сразу не послали лесом.

 

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Sign in to follow this