STM32F746GDISCOVERY. Продолжение индустриального графического интерфейса

Эта отладочная плата была приобретена в направлении других горизонтов развития, однако, как и прежде, с чего-то нужно оживлять железо. Эти отладочные платы с мониторчиками и Toush Screen – прежде всего прекрасный набор кнопок (черная и голубая в набор не входят).

Чего не хватало в предыдущем проекте калькулятора? – В основном памяти для картинок. Здесь в полном распоряжении 16 Мбайт QSPI. Можно ни на чем не экономить.

При попытке использования более-менее свежего железа всегда возникают неожиданности.

Не смотря на то, что MXCube предлагает выбор версии IAR для генерации кода, 7-я версия выдала кучу ошибок, устранить которые я не смог.

8-я версия IAR выдала ошибки инициализации DMA2D в режиме DMA2D_M2M_BLEND, обругав 2 параметра. Поскольку эти параметры мне были особо не нужны, я их просто убил.

В IAR есть кнопочки Download and Debug и Debug without Downloading

Так вот, если в программе оставить только функции инициализации и ничего значимого не делать, то при нажатии Download and Debug IAR отрабатывает Debug without Downloading. То есть загрузчик не отрабатывает и, соответственно, данные во flash память не грузятся! В примере грузятся, у Вас не грузятся. Можно хорошо скоротать несколько дней!

SDRAM

Несколько озадачило начало работы. Через программатор все работает и светится. Однако, если отключить питание и включить автономно на экране начинает все дрожать, а то появляется и совсем не пойми что. Если понажимать RESET, то вроде как все встает на свои места и начинает работать. Но со стороны комично. В STM32F429i_Discovery такого не было.

Серьезные пацаны подметили, что если включить правильное питание (жрет она 0,6 А), то не дрожит. Все, что нашел в интернете, так у кого-то были плохие конденсаторы возле SDRAM. Посмотрел через хорошую лупу – у меня точно не треснувшие!

Проблема все-таки в SDRAM. При инициализации дисплея, мы сразу привязываем его к определенным адресам буферов. А вот что на момент инициализации в этих адресах лежит не всегда понятно. При серьезном питании память, видимо, сбрасывается. При питании от USB компьютера не всегда.

Помогло! Нажимать смущенно черную кнопку после этого не нужно! Особенно я бы обратил внимание на pLayerCfg1.FBStartAdress. Поскольку уровень по цвету урезанный, то его использование не всегда очевидно, как и аппаратные телодвижения с ним разработчиков.

MPU (memory-protection-unit)

В LCD-TFT display controller (LTDC) on STM32 MCUs есть пример настройки MPU для нашей отладочной платы.

Данные в SDRAM там буферизованы для использования DMA2D,
MPU_InitStruct.IsBufferable = MPU_ACCESS_BUFFERABLE;
поэтому после использования функций библиотеки stm32746g_discovery_lcd.c вперемешку с DMA2D нужно выдавать команду SCB_CleanDCache();

Рассуждения на эту тему можно почитать в обсуждении:
https://kincajou.livejournal.com/4160197.html

Переводы AN4838, AN4839:
http://microsin.net/programming/arm/an4838-managing-memory-protection-unit-stm32.html
http://microsin.net/programming/arm/an4839-level-1-cache-stm32f7.html

QSPI

В CubeMX лапки выставить как в проекте STM32F746GDISCOVERY по умолчанию.

Настройку параметров лучше подсмотреть в примере QSPI_perfs
…Repository\STM32Cube_FW_F7_V1.15.0\Projects\STM32746G-Discovery\Applications\QSPI\QSPI_perfs\EWARM
поскольку в последнем показывается крутость производительности.

Кто не любит EWARM, нашел случайно ссылку по работе с QSPI по VisualGDB
https://sysprogs.com/w/forums/topic/using-the-quadspi-on-stm32f7-discovery/

В примере разработчики пишут в QSPI данные в формате unsigned char. Если работать со словами данных – все тоже получается. (См. STM32CubeExpansion_AN4749_F7_V1.0.0). Однако при подготовке файлов для вывода на LCD через DMA2D в формате байтов а не слов, есть нюанс.

В примере QSPI_perfs добавлена куча настроек IAR

Это линкер c секцией QSPI. Файл в текстовом формате. Можно посмотреть, можно и редактировать. Секцию .textqspi можно назвать по любому и без точки. Однако .text символизирует код и данные.

Дальше начинается самое интересное…

В примере QSPI_perfs есть файл main_images.c.

В описании AN4760 (раздел. 5.1.1 Генерация содержимого буфера кадра из памяти QSPI): «Все изображения и значки, необходимые для приложения, должны храниться во внешней памяти QSPI. В проекте доступно шесть изображений и три иконки, все они включены в файл «main_images.c», где каждое из них определяется как константа в отдельном заголовочном файле.»

Вроде бы все понятно… В stm32f746xx_QSPI_flash.icf мы создаем (уже создан разработчиками STM) раздел для памяти QSPI и директивой #pragma location = «.textqspi» мы обозначаем, что эти константы в этот раздел грузим.

Удобная штука. Все, что в «main_images.c» прописано, начинает грузиться в QSPI. Можно использовать в отдельном проекте, ничего из периферии не описывая. (Такой проект у меня вложен в основной.) Если изменить имя файла, то грузиться не будет. При этом нужно использовать линкер stm32f746xx_QSPI_flash.icf и загрузчик FlashSTM32F7xx_STM32F746G-DISCO.board. Пустую функцию dummy_init в файле «main_images.c» я тоже нигде не нашел. Возможно это намек, что именно так грузить нужно не только данные, но и код.

В следующем разделе AN4760 (5.1.2 Отображение изображений непосредственно из памяти QSPI). На этот пример (AN4749 поставляется с программным пакетом X-CUBE-LPDEMO-F7) я уже ссылался. Точно так же описываются данные. Файла main_images.c уже нет, зато в файле «nenu.c» есть функции WM_HWIN Createloadpicturefrom(void) библиотеки emWin version 5.28, описания которых я тоже поверхностно не нашел.

То есть по файлу «main_images.c» все гуманно! Работает, но не понятно как. Если кто-нибудь проникся, найдите время, пожалуйста, ПОДЕЛИТЕСЬ!

В описании AN4760 есть еще интересный подраздел «Как осуществлять программирование QSPI Flash memory только один раз».
В оригинале QUADSPI AN4760 pg. 58
How to proceed to program QSPI Flash memory only once… for IAR EWARM

Долго пытался разобраться. Так и не понял…
В Гугле ничего не нашел. Задал вопрос на форуме STMicroelectronics. Получил следующий ответ:

clive1 (NFA Crew) (Community Member)
2 months ago
If they are not part of your application image, I’d suggest writing some code to combine them, providing a table the app can access, and output them as a .HEX file, with an address starting at 0x90000000
Write that image with the STM32 Cube Programmer, using the External Loader for the QSPI memory (N25Q128 as I recall), and don’t tell IAR about it. Have you application set up the QSPI memory, and then access your table/images from there using normal memory access, ie pointers, structures, etc.

Что, собственно, и реализовано в файле QSPI_Addr_Table.h с использованием препроцессора …#ifdef IMG_NO_DATA

Но мне кажется, что это не изящно. Если кто-нибудь разобрался, пожалуйста, ПОДЕЛИТЕСЬ!

Touch panel FT5336

К stm32746g_discovery_ts.c как-то сразу возникло много вопросов…

Например функция BSP_TS_GetState, которая возвращает в строке 357 в качестве статуса
ts_status = BSP_TS_Get_GestureId(TS_State);
GestureId ну просто не работает и возвращает всегда ноль. Это не мешает разработчикам, поскольку в дефайнах статус «ОК» тоже ноль.

Строка 415 BSP_TS_ITClear с комментарием /* Clear TS IT pending bits */

Смотрим ft5336.c строка 425 /* Nothing to be done here for FT5336*/

Запросто включают и выключают режим прерываний, который не выключается, а переключается из Interrupt polling mode в Interrupt trigger mode и обратно.

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

Пришлось довольствоваться обработкой внешнего прерывания, описав

Работает как кнопка. Нажал – первое прерывание, отпустил – второе. Пока держишь TOUCH_EVENT_CONTACT. Если нажимать кнопки быстрее, чем считает TIM7, то «отжатие» теряется. Для этого пришлось добавить Flag_Lift_Up – обработку этого «отжатия».

Однако и тут промелькнула интересная деталь (хотя может быть я написал плохой обработчик). В моем алгоритме прерывания обрабатываются в зависимости от порядка их следования. При нажатии начинается опрос Touch panel пока мы не уберем руку. При «отжатии», опрос клавиш проходит только один цикл. При длительной работе калькулятора порядок этих событий иногда почему-то менялся. Это могло происходить либо из-за каких-то заморочек с volatile переменными, либо из-за каких-то помех по шине EXTI.

Так или иначе я добавил сброс флага EXTI по окончании прохода опроса кнопок при установленном флаге Flag_Lift_Up и убрал волонтльность последнего. Проблема, вроде, ушла.

В сам калькулятор добавлено:

Тригонометрия.
Если ничего не введено, то при нажатии pi это pi и выводится. Можно использовать, как операнд.  Если какие-то цифры введены, то они считаются градусами и переводятся в радианы. При этом устанавливается флаг. Если нажать еще раз, обратно в градусы. Флаг чистится. Чистится флаг еще по «С» и «СЕ».
Sin, Cos, Tan считаются из операнда в зависимости от флага в градусах или радианах. То есть если флаг не включен, то функция сама переводит градусы в радианы, но флаг не устанавливает. Если флаг установлен, то считает, что угол в радианах и тоже флаг не сбрасывает.

Вывод случайного числа от нуля до единицы с пятнадцатью знаками после запятой – rand.
Алгоритм генерации HAL_RNG_GenerateRandomNumber. Генерируются два целых 32-х разрядных числа. Переводятся в строки. Вторая приклеивается к первой. Старшие цифры обрезаются до 15. Дописывается 0. Распределение не смотрел.

Операторы div и mod выводят целую и дробную части числа со знаком в формате целых чисел.

Осторожней со степенной функцией… Все-таки STM32. ))))))))))

Проект в IAR v8.40.1.21539

С уважением Петр.

Реализуем коммерческие проекты.
Возможна работа по договору подряда.

t654rk@mail.ru

Ваши комментарии к статье:

Wordpress

Оставить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *

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

ВКонтакте
Google+