Инструменты пользователя

Инструменты сайта


prog:start:newflm

Различия

Здесь показаны различия между двумя версиями данной страницы.

Ссылка на это сравнение

Предыдущая версия справа и слева Предыдущая версия
prog:start:newflm [2018/08/23 17:39]
vasco [Результат]
prog:start:newflm [2018/11/29 20:24] (текущий)
katya
Строка 1: Строка 1:
 ======Создание FLM====== ======Создание FLM======
-FLM - это проект для Keil, который среда загружает в МК по интерфейсу Jtag или SWD. Файл FLM должен реализовать несколько функций,​ которые будут вызываться при прошивке и которым будут передаваться данные для записи в память. FLM может быть различное множество - для внутренней Flash, для записи во внешнюю память ОЗУ/​ПЗУ по внешней шине или SPI, и т.д. То-естьэто просто проект который принимает данные извне и знает что и как с ними делать,​ предварительно настроив необходимую периферию.+FLM - это проект для Keil, который среда загружает в МК по интерфейсу Jtag или SWD. Файл FLM должен реализовать несколько функций,​ которые будут вызываться при прошивке и которым будут передаваться данные для записи в память. FLM может быть различное множество - для внутренней Flash, для записи во внешнюю память ОЗУ/​ПЗУ по внешней шине или SPI, и т.д. То есть это просто проекткоторый принимает данные извне и знает что и как с ними делать,​ предварительно настроив необходимую периферию.
  
 В отличие от официальных версий,​ FLM из текущего проекта будут поддерживать стирание памяти по секторам. Что позволит использовать их совместно с утилитой J-Flash - [[prog:​start:​J-FLASH|"​Программирование контроллеров с помощью J-FLASH Lite"​]]. В отличие от официальных версий,​ FLM из текущего проекта будут поддерживать стирание памяти по секторам. Что позволит использовать их совместно с утилитой J-Flash - [[prog:​start:​J-FLASH|"​Программирование контроллеров с помощью J-FLASH Lite"​]].
Строка 31: Строка 31:
 В директорию src из исходников SPL копируем описанные выше файлы. Пак с SPL обычно устанавливается в C:​\Keil_v5\ARM\PACK\Keil\MDR1986BExx\1.4\Libraries. В директорию src из исходников SPL копируем описанные выше файлы. Пак с SPL обычно устанавливается в C:​\Keil_v5\ARM\PACK\Keil\MDR1986BExx\1.4\Libraries.
  
-Файлы описания МК (//​MDR1986VEхх.h//,​ ...) потребуются для использования структур и адресов конкретного МК. Заголовочный файл //​MDR32F9Qx_rst_clk.h//​ необходим для использования определений битов и констант для задания тактирования от HSI. Полагаться на внешние источники нельзя,​ поскольку неизвестно чем тактируется МК в изделии (резонатор,​ генератор и при каких параметрах). Из файлов //​MDR32F9Qx_eeprom.c//​ и //​MDR32F9Qx_eeprom.h//​ мы используем штатные,​ готовые функции работы с внутренней памятью Flash через контроллер EEPROM. В указанных файлах я закомментировал все, что связывало эти файлы с другими источниками.+Файлы описания МК (//​MDR1986VEхх.h//,​ ...) потребуются для использования структур и адресов конкретного МК. Заголовочный файл //​MDR32F9Qx_rst_clk.h//​ необходим для использования определений битов и констант для задания тактирования от HSI. Полагаться на внешние источники нельзя,​ поскольку неизвестночем тактируется МК в изделии (резонатор,​ генератор и при каких параметрах). Из файлов //​MDR32F9Qx_eeprom.c//​ и //​MDR32F9Qx_eeprom.h//​ мы используем штатные,​ готовые функции работы с внутренней памятью Flash через контроллер EEPROM. В указанных файлах я закомментировал все, что связывало эти файлы с другими источниками.
  
 В директорию src добавлен файл //​flmClock.c//,​ в него я вытащил реализацию перехода на частоту HSI из библиотечного //​MDR32F9Qx_rst_clk.с//​. В директорию src добавлен файл //​flmClock.c//,​ в него я вытащил реализацию перехода на частоту HSI из библиотечного //​MDR32F9Qx_rst_clk.с//​.
  
 ===Директория test=== ===Директория test===
-Функции,​ которые необходимо реализовать в FLM файле описаны [[http://​arm-software.github.io/​CMSIS_5/​Pack/​html/​algorithmFunc.html|здесь]] //(про функции подробнее дальше)//​. Для того, чтобы отладить их реализацию я создаю отдельный тестовый проект для каждого МК, реализую указанные в ссылке варианты вызовов функций,​ проверяю на МК в живую и отлаживаю. Эти же реализации функций затем используются в проектах,​ которые собирают сами FLM. При таком подходе,​ получая FLM я уверен,​ что функции с памятью работают корректно.+Функции,​ которые необходимо реализовать в FLM файле описаны [[http://​arm-software.github.io/​CMSIS_5/​Pack/​html/​algorithmFunc.html|здесь]] //(про функции подробнее дальше)//​. Для того, чтобы отладить их реализациюя создаю отдельный тестовый проект для каждого МК, реализую указанные в ссылке варианты вызовов функций,​ проверяю на МК вживую и отлаживаю. Эти же реализации функций затем используются в проектах,​ которые собирают сами FLM. При таком подходе,​ получая FLMя уверен,​ что функции с памятью работают корректно.
  
 Для примера рассмотрим создание FLM для МК 1986ВЕ92У. Поэтому в директории test я создаю поддиректорию FLM_Test_VE92 - здесь будет проект для тестирования функций FLM. //​(Раскладка памяти и периферии в серии 1986ВЕ9х одинакова,​ поэтому директорию можно было бы назвать FLM_Test_VE9х. Ведь какой-либо привязки конкретно к 1986ВЕ92 проект не имеет. Просто для отладки использовалась плата для 1986ВЕ92У.)//​ Для примера рассмотрим создание FLM для МК 1986ВЕ92У. Поэтому в директории test я создаю поддиректорию FLM_Test_VE92 - здесь будет проект для тестирования функций FLM. //​(Раскладка памяти и периферии в серии 1986ВЕ9х одинакова,​ поэтому директорию можно было бы назвать FLM_Test_VE9х. Ведь какой-либо привязки конкретно к 1986ВЕ92 проект не имеет. Просто для отладки использовалась плата для 1986ВЕ92У.)//​
  
 ===Директория FLM_Build=== ===Директория FLM_Build===
-В директории FLM_Build в одном workspace будут собраны все проекты собирающие FLM. Создание FLM рассмотрим на примере проекта для микроконтроллеров 1986ВЕ9х,​ поэтому создаем директорию VE9x_FLM_FlashInt. В нее сейчас и будем создавать проект.+В директории FLM_Build в одном workspace будут собраны все проектысобирающие FLM. Создание FLM рассмотрим на примере проекта для микроконтроллеров 1986ВЕ9х,​ поэтому создаем директорию VE9x_FLM_FlashInt. В нее сейчас и будем создавать проект.
 =====Создаем проект FLM===== =====Создаем проект FLM=====
 Шаблон проекта для создания FLM находится в директории с готовыми алгоритмами - C:​\Keil_v5\ARM\Flash. Из этой директории нам понадобятся:​ Шаблон проекта для создания FLM находится в директории с готовыми алгоритмами - C:​\Keil_v5\ARM\Flash. Из этой директории нам понадобятся:​
Строка 66: Строка 66:
  
 ===Код FlashDev.c для 1986ВЕ9х=== ===Код FlashDev.c для 1986ВЕ9х===
-Основные параметры взяты из спецификации. Таймаут для операций я указал в 5 секунд,​ надеюсь что этого достаточно. Параметры указанные в этом файле, будут использоваться Keil при стирании и записи страниц памяти.+Основные параметры взяты из спецификации. Таймаут для операций я указал в 5 секунд,​ надеюсь что этого достаточно. Параметрыуказанные в этом файле, будут использоваться Keil при стирании и записи страниц памяти.
  
 <​code>​ <​code>​
Строка 91: Строка 91:
  
 ===Код FlashDev.c для 1986ВЕ1Т/​1986ВЕ3Т=== ===Код FlashDev.c для 1986ВЕ1Т/​1986ВЕ3Т===
-Для МК 1986Е1Т и 1986ВЕ3Т раскладка памяти так-же одинакова,​ как и само ядро Cortex-M1. Поэтому для этих МК собирается тоже один FLM на двоих. Помимо раскладки памяти следует учитывать вопросы тактирования,​ но эти МК переводятся на тактирование от HSI одинаково,​ поэтому проблемы в использовании одного FLM на двоих нет.+Для МК 1986Е1Т и 1986ВЕ3Т раскладка памяти также одинакова,​ как и само ядро Cortex-M1. Поэтому для этих МК собирается тоже один FLM на двоих. Помимо раскладки памяти следует учитывать вопросы тактирования,​ но эти МК переводятся на тактирование от HSI одинаково,​ поэтому проблемы в использовании одного FLM на двоих нет.
  
 <​code>​ <​code>​
Строка 114: Строка 114:
 </​code>​ </​code>​
  
-Отдельно остановлюсь на последней строке. В начальном варианте проектая неправильно понял назначение этих параметров. Исправиться помог Владимир из техподдержки Миландр,​ за что ему большое спасибо!+Отдельно остановлюсь на последней строке. В начальном варианте проекта я неправильно понял назначение этих параметров. Исправиться помог Владимир из техподдержки Миландр,​ за что ему большое спасибо!
  
 <​code>​ <​code>​
Строка 123: Строка 123:
 Здесь есть небольшая путаница. В терминах FLM, сектор - это часть памяти (адресного пространства от и до), которая может быть стерта за раз. В спецификации на микроконтроллер это соответствует странице памяти. Внутренняя память МК состоит из 32 страниц,​ каждую из которых можно стереть по отдельности. Если смотреть далее по спецификации,​ то каждая страница в свою очередь состоит из 4 секторов. Но эти сектора в памяти страницы - совсем не то, что подразумевает FLM. Итого, параметры означают следующее:​ Здесь есть небольшая путаница. В терминах FLM, сектор - это часть памяти (адресного пространства от и до), которая может быть стерта за раз. В спецификации на микроконтроллер это соответствует странице памяти. Внутренняя память МК состоит из 32 страниц,​ каждую из которых можно стереть по отдельности. Если смотреть далее по спецификации,​ то каждая страница в свою очередь состоит из 4 секторов. Но эти сектора в памяти страницы - совсем не то, что подразумевает FLM. Итого, параметры означают следующее:​
   * 0x00001000 - размер одной страницы. Адреса с таким шагом будут подаваться в функцию EraseSector(adr). При записи программы,​ J-Flash или Keil считают сколько нужно стереть страниц и вызывают EraseSector() с адресами,​ кратными размеру страницы памяти микроконтроллера.   * 0x00001000 - размер одной страницы. Адреса с таким шагом будут подаваться в функцию EraseSector(adr). При записи программы,​ J-Flash или Keil считают сколько нужно стереть страниц и вызывают EraseSector() с адресами,​ кратными размеру страницы памяти микроконтроллера.
-  * 0x00000000 - стартовый адрес памяти,​ относительно адреса указанного выше в структуре - Device Start Address.+  * 0x00000000 - стартовый адрес памяти,​ относительно адресауказанного выше в структуре - Device Start Address.
  
 Например,​ если зашиваемая программа занимает порядка 3 секторов,​ то будет вызвано стирание трех страниц (на примере 1986ВЕ9х):​ Например,​ если зашиваемая программа занимает порядка 3 секторов,​ то будет вызвано стирание трех страниц (на примере 1986ВЕ9х):​
Строка 133: Строка 133:
 </​code>​ </​code>​
  
-Остальные страницы не будут стираться чтобы сэкономить ресурс flash памяти,​ который составляет порядка 10-20 тысяч циклов перезаписи. Причем Keil, в отличие от J-Flash, поступает еще хитрее. Keil сначала проверяет страницу на стертость,​ и если страница стерта,​ то он пропускает стирание этой страницы и переходит к следующей. J-Flash же честно вызывает EraseSector() для каждой страницы,​ вне зависимости пустая она или нет.+Остальные страницы не будут стираться чтобы сэкономить ресурс flash памяти,​ который составляет порядка 10-20 тысяч циклов перезаписи. Причем Keil, в отличие от J-Flash, поступает еще хитрее. Keil сначала проверяет страницу на стертость,​ и если страница стерта,​ то он пропускает стирание этой страницы и переходит к следующей. J-Flash же честно вызывает EraseSector() для каждой страницы,​ вне зависимости ​от того ​пустая она или нет.
  
-Необходимость с указанием размера и относительного адреса связана с тем, что память может быть устроена по разному. Например в этом примере от [[http://​www.keil.com/​pack/​doc/​CMSIS/​Pack/​html/​flashAlgorithm.html#​AddFPA|ARM]],​ представлена память,​ где размер страниц в адресном пространстве разный:​+Необходимость с указанием размера и относительного адреса связана с тем, что память может быть устроена по-разному. Напримерв этом примере от [[http://​www.keil.com/​pack/​doc/​CMSIS/​Pack/​html/​flashAlgorithm.html#​AddFPA|ARM]],​ представлена память,​ где размер страниц в адресном пространстве разный:​
  
 <​code>​ <​code>​
Строка 156: Строка 156:
   * от 0x00030000 до 0x00040000, расположено 8 страниц размером по 0x002000 - 8кБ.   * от 0x00030000 до 0x00040000, расположено 8 страниц размером по 0x002000 - 8кБ.
  
-На самом деле средние большие страницы по 64КБ могут таковыми и не быть, важно чтобы функция EraseSector() при обращении к ней с адресами 0х10000 и 0х20000 стирала по 64КБ.+На самом делесредние большие страницы по 64КБ могут таковыми и не быть. Важно чтобы функция EraseSector() при обращении к ней с адресами 0х10000 и 0х20000 стирала по 64КБ.
 ====Реализация функций - FlashPrg.c==== ====Реализация функций - FlashPrg.c====
 Файл //​FlashPrg.c//​ должен реализовать функции для работы FLM. Поскольку эти же функции мы будем использовать в тестовом проекте,​ то файл //​FlashPrg.c//​ переносим в директорию src. И так как функции работы с EEPROM из файла MDR32F9Qx_eeprom.c работают со всеми МК, то файл //​FlashPrg.c//​ потребуется всего один на все проекты. Файл //​FlashPrg.c//​ должен реализовать функции для работы FLM. Поскольку эти же функции мы будем использовать в тестовом проекте,​ то файл //​FlashPrg.c//​ переносим в директорию src. И так как функции работы с EEPROM из файла MDR32F9Qx_eeprom.c работают со всеми МК, то файл //​FlashPrg.c//​ потребуется всего один на все проекты.
Строка 193: Строка 193:
 </​code>​ </​code>​
  
-В коде данной функции необходимо учитывать,​ что в момент начала работы прошивальщика,​ МК может быть настроен произвольным образом. Т.еработать на какой-то неизвестной частоте,​ с периферией и прерываниями. Следовательно необходимо все это отключить. ​ \\ +В коде данной функции необходимо учитывать,​ что в момент начала работы прошивальщика,​ МК может быть настроен произвольным образом. То есть ​работать на какой-то неизвестной частоте,​ с периферией и прерываниями. Следовательно необходимо все это отключить. ​ \\ 
-//(В первых версиях кода я этого не делал, поэтому прошивка завершалась успешно только со второго раза. Как предполагаю,​ с первого раза портилась текущая программа,​ а со второго раза не происходил запуск испорченной программы,​ МК оставался работать в настройках по сбросу и тогда FLM отрабатывал полностью правильно.)//​+//(В первых версиях кода я этого не делал, поэтому прошивка завершалась успешно только со второго раза. Как предполагаю,​ с первого раза портилась текущая программа,​ а со второго раза не происходил запуск испорченной программы,​ МК оставался работать в настройках по сбросуи тогда FLM отрабатывал полностью правильно.)//​
  
-Из входных параметров я использую только //fnc//, для того чтобы включить тактирование блока EEPROM, если будут операции стирания и записи. При верификации я читаю память напрямую,​ без блока EEPROM. Но если FLM будет модифицироваться для работы с информационной памятьюили будет выставлена опция в коде READ_BY_EEPROM,​ то тактирование на RST_CLK_PCLK_EEPROM должно подаваться и в операциях верификации.+Из входных параметров я использую только //fnc//, для того чтобы включить тактирование блока EEPROM, если будут операции стирания и записи. При верификации я читаю память напрямую,​ без блока EEPROM. Но если FLM будет модифицироваться для работы с информационной памятью или будет выставлена опция в коде READ_BY_EEPROM,​ то тактирование на RST_CLK_PCLK_EEPROM должно подаваться и в операциях верификации.
  
 Переход на частоту HSI производится функцией //​ClocksDeinit_HSI()//,​ которая реализована в //​src/​flmClock.c//​. Переход на частоту HSI производится функцией //​ClocksDeinit_HSI()//,​ которая реализована в //​src/​flmClock.c//​.
Строка 226: Строка 226:
 </​code>​ </​code>​
  
-Функция //​UnInit()//​ выключает тактирование с блока EEPROM, предварительно остановив работу блока через регистры. Исполнение алгоритма может сбиться или зависнуть. Если таймаут операции закончится,​ то прошивальщик Keil вызовет процедуру //​UnInit()//​ в процессе работы для того чтобы остановить исполнение.  +Функция //​UnInit()//​ выключает тактирование с блока EEPROM, предварительно остановив работу блока через регистры. Исполнение алгоритма может сбиться или зависнуть. Если таймаут операции закончится,​ то прошивальщик Keil вызовет процедуру //​UnInit()//​ в процессе работы для тогочтобы остановить исполнение.  
-//(В коде других производителей можно увидеть применение сторожевых таймеров,​ чтобы предотвратить возможные сбои при работе FLM. Например применение FLM не к месту "убъет" тактирование ядра, то Jtag отвалится и никакие UnInit() уже не помогут - спасет сторожевой таймер.)//​+//(В коде других производителей можно увидеть применение сторожевых таймеров,​ чтобы предотвратить возможные сбои при работе FLM. Напримерприменение FLM не к месту "убьет" тактирование ядра, тогда ​Jtag отвалитсяи никакие UnInit() уже не помогут - спасет сторожевой таймер.)//​
  
-В конце кода //​UnInit()//​ идет обращение в произвольным ячейка в разных страницах памяти. Дело в том, что например в 1986ВЕ1Т,​ ускоритель Flash памяти после операции записи не обновляет свое содержимое из обновленной памяти и может вернуть предыдущее значение. Доступ к произвольным ячейкам должен заставить ускоритель обновить данные. По крайней мере, такой код был добавлен в официальный FLM для 1986ВЕ1Т - 1986BE1_rev2.FLM.+В конце кода //​UnInit()//​ идет обращение в произвольным ячейкам в разных страницах памяти. Дело в том, чтонапримерв 1986ВЕ1Т,​ ускоритель Flash памяти после операции записи не обновляет свое содержимое из обновленной памяти и может вернуть предыдущее значение. Доступ к произвольным ячейкам должен заставить ускоритель обновить данные. По крайней мере, такой код был добавлен в официальный FLM для 1986ВЕ1Т - 1986BE1_rev2.FLM.
  
 ===EraseChip,​ EraseSector,​ ProgramPage=== ===EraseChip,​ EraseSector,​ ProgramPage===
Строка 275: Строка 275:
  
 ===BlankCheck,​ Verify=== ===BlankCheck,​ Verify===
-Для реализации следующих двух функций я добавил функцию чтения слова //​ReadWord()//​. В этой функции выбирается чтение напрямую или через контроллер EEPROM. В функцию BlankCheck() передается параметр pat, это значение стертого байта из файла FlashDev.c. В текущем коде я им не пользовался,​ поскольку в Миландр стертое слово ​ всегда равно 0xFFFFFFFF.+Для реализации следующих двух функций я добавил функцию чтения слова //​ReadWord()//​. В этой функции выбирается чтение напрямую или через контроллер EEPROM. В функцию BlankCheck() передается параметр pat, это значение стертого байта из файла FlashDev.c. В текущем коде я им не пользовался,​ поскольку в микроконтроллерах ​Миландр стертое слово ​ всегда равно 0xFFFFFFFF.
  
 <​code>​ <​code>​
Строка 335: Строка 335:
 </​code>​ </​code>​
  
-При отладке функций обнаружилось,​ что изредка чтение некоторых ячеек дает неправильный результат. Обычно это происходит в 1986ВЕ1Т после стирания всего чипа. Не вполне понял с чем это связано,​ виноват ускоритель Flash или что-то иное, но добавление двойного считывания в случае сбоя помогло при прогоне тестов. Сбои прекратились,​ поэтому опция с двойным чтении осталась в коде. Позднее были собраны отдельные проекты с этой опцией,​ чтобы сравнить на сколько она необходима. Проекты и конечные FLM отличаются от тех, что с двойным чтением суффиксом _DR (DoubleRead) - например,​ //​1986VE9x_FlashInt_DR.FLM//​. Мнение о необходимости DoubleRead пока не сложилось.+При отладке функций обнаружилось,​ что изредка чтение некоторых ячеек дает неправильный результат. Обычно это происходит в 1986ВЕ1Т после стирания всего чипа. Не вполне понялс чем это связано,​ виноват ускоритель Flash или что-то иное, но добавление двойного считывания в случае сбоя помогло при прогоне тестов. Сбои прекратились,​ поэтому опция с двойным чтении осталась в коде. Позднее были собраны отдельные проекты с этой опцией,​ чтобы сравнить на сколько она необходима. Проекты и конечные FLM отличаются от тех, что с двойным чтением суффиксом _DR (DoubleRead) - например,​ //​1986VE9x_FlashInt_DR.FLM//​. Мнение о необходимости DoubleRead пока не сложилось.
  
 =====Необходимость функций===== =====Необходимость функций=====
Строка 347: Строка 347:
 Создается workspace в меню Keil - //Project - New Multy-Project Workspace...//,​ далее необходимо дать название - у меня получился //​FLM_Build.uvmpw//​. После задания имени откроется окно менеджера проектов,​ в котором можно выбрать проекты для добавление в workspace. Создается workspace в меню Keil - //Project - New Multy-Project Workspace...//,​ далее необходимо дать название - у меня получился //​FLM_Build.uvmpw//​. После задания имени откроется окно менеджера проектов,​ в котором можно выбрать проекты для добавление в workspace.
  
-Активным может быть только один проект,​ для него открываются опции проекта и только его можно редактировать. Чтобы поменять активный проект надо кликнуть на необходимы проект правой клавишей мыши и выбрать //Set as Active Project//.+Активным может быть только один проект,​ для него открываются опции проекта и только его можно редактировать. Чтобы поменять активный проектнадо кликнуть на необходимый проект правой клавишей мыши и выбрать //Set as Active Project//.
 Для добавления и удаления проектов необходимо правой мышью кликнуть на заголовок workspace и выбрать //Manage Multy-Project Workspace...//​. Для добавления и удаления проектов необходимо правой мышью кликнуть на заголовок workspace и выбрать //Manage Multy-Project Workspace...//​.
  
-После добавления всех проектов в workspace нажимаем на панели кнопку //Batch Build//, при этом откроется окно ​где ​необходимо выбрать проекты,​ которые будут собираться. Варианты с ARM7_ARM9 нам не нужны, остальные выбираем.+После добавления всех проектов в workspace нажимаем на панели кнопку //Batch Build//, при этом откроется окно, в котором ​необходимо выбрать проекты,​ которые будут собираться. Варианты с ARM7_ARM9 нам не нужны, остальные выбираем.
 После сборки проектов //Build// в директории FLM_Build получаем файлы FLM. После сборки проектов //Build// в директории FLM_Build получаем файлы FLM.
  
Строка 358: Строка 358:
  
 =====Результат===== =====Результат=====
-Полученные FLM проверены на МК 1986ВЕ1Т,​ 1986ВЕ3Т и 1986ВЕ9х. Прошивка происходит,​ но не со 100% результатом. Иногда выдаются сбои верификации. Например,​ при прошивке через J-Flash выдается статус,​ что верификация провалена. При этом программа прошивается и работает. Если же запустить прошивку второй раз ​ то она не происходит,​ а выдается сообщение,​ что программа уже зашита и верификация зашитой программы прошла успешно.+Полученные FLM проверены на МК 1986ВЕ1Т,​ 1986ВЕ3Т и 1986ВЕ9х. Прошивка происходит,​ но не со 100% результатом. Иногда выдаются сбои верификации. Например,​ при прошивке через J-Flash выдается статус,​ что верификация провалена. При этом программа прошивается и работает. Если же запустить прошивку второй раз то она не происходит,​ а выдается сообщение,​ что программа уже зашита и верификация зашитой программы прошла успешно.
  
 Будем разбираться с этим дальше. Будем разбираться с этим дальше.
Строка 366: Строка 366:
 <WRAP center round important 90%> <WRAP center round important 90%>
 Обратите внимание,​ в спецификации на микроконтроллеры указано - **"​При стирании Обратите внимание,​ в спецификации на микроконтроллеры указано - **"​При стирании
-информационной областиавтоматически стирается и основная"​**. ​+информационной области автоматически стирается и основная"​**. ​
 </​WRAP>​ </​WRAP>​
  
-Это совсем не очевидно и попалось на глаза ​крайне ​случайно. Стоит иметь это ввидупри работе с информационной памятью.+Это совсем не очевидно и попалось на глаза случайно. Стоит иметь это ввиду при работе с информационной памятью.
  
 ===Тестовые проекты=== ===Тестовые проекты===
-Тестовые проекты описывать не буду, код представлен в директории test. Проекты имитируют последовательность вызовов функций FlashPrg.c прошивальщиком Keil. Это обычные проекты для работы с МКс той лишь особенностью,​ что они собраны для запуска из ОЗУ и поэтому работают только в режиме отладки. Но, собственно,​ этого достаточно.+Тестовые проекты описывать не буду, код представлен в директории test. Проекты имитируют последовательность вызовов функций FlashPrg.c прошивальщиком Keil. Это обычные проекты для работы с МК с той лишь особенностью,​ что они собраны для запуска из ОЗУ и поэтому работают только в режиме отладки. Но, собственно,​ этого достаточно.
  
  
prog/start/newflm.txt · Последние изменения: 2018/11/29 20:24 — katya