Загрузка кода в mega 2560
В рамках моего приложения мне нужно иметь возможность обновить код на mega 2560 в поле с помощью загрузки из Интернета.
Я нашел этот код в техническом паспорте AT Mega 2560
;-подпрограмма записывает одну страницу данных из оперативной памяти во флэш
-память ; на первое место данных в оперативной памяти указывает указатель Y
; на первое место данных во флэш-памяти указывает указатель Z
;-обработка ошибок не включена
;-программа должна быть помещена в загрузочное пространство
; (по крайней мере, подпрограмма Do_spm). Только код внутри раздела NRWW может
быть прочитан во время самопрограммирования (стирание страницы и запись страницы).
;-используемые регистры: r0, r1, temp1 (r16), temp2 (r17), looplo (r24),
; loophi (r25), spmcrval (r20)
; хранение и восстановление регистров не входит в подпрограмму
; использование регистра может быть оптимизировано за счет размера кода
;-Предполагается, что либо таблица прерываний перемещается в загрузочную
; раздел загрузчика или что прерывания отключены
..equ PAGESIZEB = PAGESIZE*2 ;PAGESIZEB is page size in BYTES, not words
.org SMALLBOOTSTART
Write_page:
; Page Erase
ldi spmcrval, (1<<PGERS) | (1<<SPMEN)
call Do_spm
; re-enable the RWW section
ldi spmcrval, (1<<RWWSRE) | (1<<SPMEN)
call Do_spm
; transfer data from RAM to Flash page buffer
ldi looplo, low(PAGESIZEB) ;init loop variable
ldi loophi, high(PAGESIZEB) ;not required for PAGESIZEB<=256
Wrloop:
ld r0, Y+
ld r1, Y+
ldi spmcrval, (1<<SPMEN)
call Do_spm
adiw ZH:ZL, 2
sbiw loophi:looplo, 2 ;use subi for PAGESIZEB<=256
brne Wrloop
; execute Page Write
subi ZL, low(PAGESIZEB) ;restore pointer
sbci ZH, high(PAGESIZEB) ;not required for PAGESIZEB<=256
ldi spmcrval, (1<<PGWRT) | (1<<SPMEN)
call Do_spm
; re-enable the RWW section
ldi spmcrval, (1<<RWWSRE) | (1<<SPMEN)
call Do_spm
; read back and check, optional
ldi looplo, low(PAGESIZEB) ;init loop variable
ldi loophi, high(PAGESIZEB) ;not required for PAGESIZEB<=256
subi YL, low(PAGESIZEB) ;restore pointer
sbci YH, high(PAGESIZEB)
Rdloop:
elpm r0, Z+
ld r1, Y+
cpse r0, r1
jmp Error
sbiw loophi:looplo, 1 ;use subi for PAGESIZEB<=256
brne Rdloop
; return to RWW section
; verify that RWW section is safe to read
Return:
in temp1, SPMCSR
sbrs temp1, RWWSB ; If RWWSB is set, the RWW section is not ready yet
ret
; re-enable the RWW section
ldi spmcrval, (1<<RWWSRE) | (1<<SPMEN)
call Do_spmr
jmp Return
Do_spm:
; check for previous SPM complete
Wait_spm:
in temp1, SPMCSR
sbrc temp1, SPMEN
rjmp Wait_spm
; input: spmcrval determines SPM action
; disable interrupts if enabled, store status
in temp2, SREG
cli
; check that no EEPROM write access is present
Wait_ee:
sbic EECR, EEPE
rjmp Wait_ee
; SPM timed sequence
out SPMCSR, spmcrval
spm
; restore SREG (to enable interrupts if originally enabled)
out SREG, temp2
ret
Я пытаюсь преобразовать это в код, который я могу использовать в своем проекте arduino в разделе проводка. Мой первый вопрос-это реестр. Похоже,
что spmcrval-это регистр 20, но как я могу получить доступ к этому регистру из моего проекта arduino?
Я нашел константы, такие как SPMEN
в заголовке arduino, но не эти имена регистров.
Кроме того, не стесняйтесь, если хотите, избежать драмы и сказать: "Вот исходный код C", который будет стоить определенного поклонения герою.
Похоже, все использует avrdude, и поэтому я пытаюсь разобрать и это.
@Thom, 👍2
Обсуждение1 ответ
Лучший ответ:
Только из раздела загрузчика можно писать во flash на ATmega2560. Optiboot 8 имеет функцию do_spm для записи во flash. Он доступен через заголовочный файл, доступный в примерах в репозитории OptibootGitHub.
После того, как обновленный двоичный файл приложения будет записан в свободную часть флэш-памяти запущенным приложением, необходимо скопировать обновленное приложение в место запуска с адреса 0. Это должно быть сделано снова загрузчиком.
Сборки Optiboot в MCUdude Mega Core и Mighty Core имеют Optiboot, усиленный моей функцией copy_flash_pages, которая копирует страницы, а затем сбрасывает MCU.
Моя библиотека ArduinoOTA использует функции do_spm и copy_flash_pages для хранения и применения загруженного двоичного файла скетча. Объект InternalStorage также можно использовать для применения загруженного двоичного файла.
То, что я вижу, обрабатывает загрузки. Есть ли здесь что-то, что устанавливает эти загрузки в Mega 2560? Я отталкиваюсь от планшета., @Thom
это самообновление. вызов InternalStorage.apply заменяет скетч загруженным двоичным файлом, @Juraj
разместил еще один вопрос здесь: https://arduinoprosto.ru/q/85142/program-a-mega2560-from-a-different-serial-port о том, как изменить последовательный порт на тот, который используется HC-05. не могу найти пример, но он кажется простым., @Thom
- Запустить Timer1 в ATmega2560 со сборкой
- Mega2560 программирование avrdude мегакора: Device signature = 0x000000
- Не могу вызывать указатели функций С++ из встроенной сборки
- Можно загрузить скетч Arduino только один раз на пользовательскую плату Mega2560
- Будет ли загрузчик обмениваться данными через TX0 / RX0
- Как записать загрузчик?
- Не удается снова загрузиться после смены платы
- Разница в загрузчике Arduino Nano ATmega328P
https://github.com/jandrassy/ArduinoOTA/blob/master/examples/Advanced/OTASketchDownload/OTASketchDownload.ino, @Juraj