• Система автоматизации с открытым исходным кодом на базе esp8266/esp32 микроконтроллеров и приложения IoT Manager. Наша группа в Telegram

Стартовый адрес irom0_text

Garmin

Member
При компиляции тестового примера "lwip_open_demo_app" из последнего UDK при изменении размера прошивки в файле Makefile в корне проекта объём памяти не изменяется. Линкер берёт размер памяти из файла
"C:\Espressif\ESP8266_SDK\ld\eagle.app.v6.ld" .
Если ручками изменить размер памяти в строке
" irom0_0_seg : org = 0x40240000, len = 0xBC000",
то компиляция проходит нормально сновым размером памяти.
Однако, в этом каталоге есть ещё файлы для различных объёмов памяти, да ещё с разными опциями.
Все файлы отличаются одной строкой. Причём не только размером памяти, но и стартовым адресом.
Теперь вопрос:
Какой стартовый адрес irom правильный:
- 0x40201010
- 0x40211000
- 0x40240000
- 0x40251000
- 0x40281010
- 0x40291000
И от чего зависит стартовый адрес irom?
Ибо приходится править ручками всё, а зависимость я в гугле не нашёл.
 

Garmin

Member
Я вижу, что начиная с адреса 0x40100000 грузится в iram User Code из первой половины flash. Это не кешируемые функции.
SPI flash отображается в адресном пространстве, начиная с 0x40200000
Для чего даётся свободное пространство перед началом кода?
Где увидеть необходимый размер сдвига?
Для чего нужны конфигурации app1 и app2 в ld файлах?
 

pvvx

Активный участник сообщества
Flash находиться в виртуальном “кешируемом” адресном пространстве 1 мегабайт с адреса 0x40200000.

Но с неё грузится и начальный код в IRAM с таблицей разметки, расположенной в начальных адресах Flash. На размер этого загружаемого кода и получается смещение исполняемого кода в окне “кеша” Flash (куда отображается flash).

IRAM– это область памяти в 64 килобайта с 0x40100000 для исполняемого кода (доступ только по 32 бита), из которой SDK использует верхние 32 килобайта под “кеш” – для подгрузки кода c Flash. Можно на “кеш” оставить и 16 килобайт, тогда доступная для не “кешируемого” кода IRAM выходит 48 килобайт. Скорость и потребление модулем за счет убавления размера отведенного на “кеш” это практически не увеличивает и не уменьшает, но увеличивает доступную память. Требуется если много критического кода и для подгрузки больших “оверлеев”. В моем meSDK это опционально – выбирает пользователь при трансляции. Китайские SDK и “лоадеры” этого сделать не позволяют.
-------
Из-за аппаратных ограничений работы “кеша” в 1 мегабайт с начала Flash китайцы делают свою кривую разметку на несколько flash, путем переключения CS у QSPI…
Разные “app1 и app2 в ld файлах” нужны для ATA или для двух разных прошивок и переключения их с помощью загрузчика. Но китайские SDK уже давно не лезут в 1 мегабайт...
 
Последнее редактирование:

Garmin

Member
Вот это замечательный ответ!
То есть. если после компиляции я получаю например, такую табличку:
Код:
------------------------------------------------------------------------------
   Section|                   Description| Start (hex)|   End (hex)|Used space
------------------------------------------------------------------------------
      data|        Initialized Data (RAM)|    3FFE8000|    3FFE83C6|     966
    rodata|           ReadOnly Data (RAM)|    3FFE83C8|    3FFE8BA8|    2016
       bss|      Uninitialized Data (RAM)|    3FFE8BA8|    3FFEED98|   25072
      text|          Uncached Code (IRAM)|    40100000|    40106BD6|   27606
irom0_text|             Cached Code (SPI)|    40240000|    4026EA04|  190980
------------------------------------------------------------------------------
Здесь размер IRAM равен 0x6BD6 (27606 байт). Значит, начальный адрес irom0 должен быть немного больше, например 0x40206C00 или ox40207000.
Также размер сегмента iram1 может быть указан len=0x7000. Отсюда для этого проекта допустимые параметры в файле eagle.app.v6.ld
Код:
MEMORY
{
  dport0_0_seg :                        org = 0x3FF00000, len = 0x10
  dram0_0_seg :                         org = 0x3FFE8000, len = 0x03000
  iram1_0_seg :                         org = 0x40100000, len = 0x7000
  irom0_0_seg :                         org = 0x40207000, len = 0xF5000
}
и я автоматом получаю 36,8 к кэша iram (0x10000 - 0x7000 = 0x9000)
Размер допустимой памяти для флэша 1Мбит под irom0 0x100000 - 0x03000 - 0x7000 = F6000, ну и оставим место для dport0 - F5000

А теперь, если эти рассуждения правильные, получается, что файл eagle.app.v6.ld нужно править под конкретный проект. Тогда его место не в служебном каталоге, а в проекте. Отсюда нужно изменять makefile. (ПОМОГИТЕ!!! :O)

B в корневом makefile есть строчки с выбором размера флэш:
Код:
SPI_SIZE_MAP ?= 2
ifeq ($(SPI_SIZE_MAP), 1)
   size_map = 1
   flash = 256
   flashimageoptions += -fs 2m
else
   ifeq ($(SPI_SIZE_MAP), 2)
     size_map = 2
     flash = 1024
     flashimageoptions += -fs 8m
   else
     ifeq ($(SPI_SIZE_MAP), 3)
       size_map = 3
       flash = 2048
       flashimageoptions += -fs 16m
     else
       ifeq ($(SPI_SIZE_MAP), 4)
         size_map = 4
         flash = 4096
         flashimageoptions += -fs 32m
       else
         ifeq ($(SPI_SIZE_MAP), 5)
           size_map = 5
           flash = 2048
           flashimageoptions += -fs 16m
         else
           ifeq ($(SPI_SIZE_MAP), 6)
             size_map = 6
             flash = 4096
             flashimageoptions += -fs 32m
           else
           size_map = 0
           flash = 512
           flashimageoptions += -fs 4m
           endif
         endif
       endif
     endif
   endif
endif
Тогда для чего нужны переменные size_map, flash, flashimageoptions?
Отвечу сам себе:
flashimageoptions используется для программирования и утилиты elf2image
flash - для make
А size_map нигде не используется :))
 
Последнее редактирование:

pvvx

Активный участник сообщества
Здесь размер IRAM равен 0x6BD6 (27606 байт). Значит, начальный адрес irom0 должен быть немного больше, например 0x40206C00 или ox40207000.
Также размер сегмента iram1 может быть указан len=0x7000. Отсюда для этого проекта допустимые параметры в файле eagle.app.v6.ld
...
и я автоматом получаю 36,8 к кэша iram (0x10000 - 0x7000 = 0x9000)
Немного не так - в начале flash находится не только код копируемый для исполнения в IRAM, но и данные для инициализации data и rodata.
Это все описывается в заголовке сегментов для загрузчика. Обычно загрузчик грузит (переписывает из flash) три сегмента - код в IRAM, и два блока инициализации в RAM (data и rodata). Эти три сегмента с разметкой загрузчику и занимают начальную неиспользуемую далее часть flash.
Так-же в flash есть области для записи настроек. Их тоже исключают из виртуального "кешируемого" пространства.

И у IRAM, в стандартных проектах от китайцев всегда 32 килобайта.
iram1_0_seg : org = 0x40100000, len = 0x8000
 
Последнее редактирование:

Garmin

Member
По результатам проверки у меня всё получилось.
Мой проект "UDP_SPI_project" сделан на базе примера "lwip_open_demo_app", поэтому структура папок соответствует этому проекту.
Что я сделал:
1) скопировал файл "eagle.app.v6.ld" в корень моего проекта
2) в папке /app в файле "makefile" закомментировал строку
#LD_FILE = $(LDDIR)/eagle.app.v6.ld
и вместо неё написал:
LD_FILE = c:/Espressif/examples/UDP_SPI_project/eagle.app.v6.ld3
В моём файле "eagle.app.v6.ld" изменил параметры:
Код:
MEMORY
{
  dport0_0_seg :  org = 0x3FF00000, len = 0x10
  dram0_0_seg :  org = 0x3FFE8000, len = 0x14000
  iram1_0_seg :  org = 0x40100000, len = 0x8000
  irom0_0_seg :  org = 0x40210000, len = 0xE0000
}
В результате компиляции получил такое распределение памяти:
Код:
Sections:
Idx Name          Size      VMA       LMA       File off  Algn
  0 .data         0000047a  3ffe8000  3ffe8000  000000e0  2**4
                  CONTENTS, ALLOC, LOAD, DATA
  1 .rodata       000018a8  3ffe8480  3ffe8480  00000560  2**3
                  CONTENTS, ALLOC, LOAD, READONLY, DATA
  2 .bss          000073c8  3ffe9d28  3ffe9d28  00001e08  2**4
                  ALLOC
  3 .text         00007b06  40100000  40100000  00001e08  2**2
                  CONTENTS, ALLOC, LOAD, READONLY, CODE
  4 .irom0.text   0003e044  40210000  40210000  00009910  2**4
                  CONTENTS, ALLOC, LOAD, READONLY, CODE
------------------------------------------------------------------------------
   Section|                   Description| Start (hex)|   End (hex)|Used space
------------------------------------------------------------------------------
      data|        Initialized Data (RAM)|    3FFE8000|    3FFE847A|    1146
    rodata|           ReadOnly Data (RAM)|    3FFE8480|    3FFE9D28|    6312
       bss|      Uninitialized Data (RAM)|    3FFE9D28|    3FFF10F0|   29640
      text|          Uncached Code (IRAM)|    40100000|    40107B06|   31494
irom0_text|             Cached Code (SPI)|    40210000|    4024E044|  254020
------------------------------------------------------------------------------
Entry Point : 40100004 call_user_start()
Total Used RAM : 37098
Free RAM : 44822
Free IRam : 1274 or 17658 if 48k IRam
------------------------------------------------------------------------------
Generate 0x00000.bin and 0x40000.bin successully in folder firmware.
0x00000.bin-------->0x00000
0x40000.bin-------->0x40000
Done
Теперь вопрос по отчёту.
bin файлы показывают адреса с 0x40000. То есть реально во флеше 1М есть место для 0xС0000 адресов - 786кБайт?
Тогда нельзя ставить размер irom0 0xE0000. Подскажите, как правильно.
 

pvvx

Активный участник сообщества
По результатам проверки у меня всё получилось.
Код:
Generate 0x00000.bin and 0x40000.bin successully in folder firmware.
0x00000.bin-------->0x00000
0x40000.bin-------->0x40000
bin файлы показывают адреса с 0x40000.
Это только название файла и оно не корректно к адресам во Flash.
irom0_text| Cached Code (SPI)| 40210000| 4024E044| 254020
Значит 0x40000.bin вам нужно грузить в адрес 0x10000 у Flash.

По этому я вынес адрес irom0_text в переменную ADDR_FW2 в makefile и он должен соответствовать указанному в irom0_text в eagle.app.v6.ld
Можно написать автогенерацию этой части ld файла или наоборот - считывать из ld значения и применять в makefile. Но на это нет особого желания, т.к. изменяется редко, под проект.
Пример вычисления адреса свободной области за irom0_text c кратностью к адресу сектора в flash для записи туда web-диска или других данных пользователя...
 
Последнее редактирование:

Garmin

Member
Благодарю, но у меня Makefile другой, я попробовал добавить переменную, однако сомневаюсь в результате прошивки.
 
Сверху Снизу