Jump to content

    

AVI-crak

Участник
  • Content Count

    239
  • Joined

  • Last visited

Everything posted by AVI-crak


  1. Освоение ARM контроллеров

    Цитата(esaulenka @ Apr 5 2016, 02:33) Но вот правда - бросайте Вы эти глупости. Мне кажется, этим ремапом никто толком и не пользуется. Ремамп - единственный корректный способ залить код в внешнюю sdram из внешней 25qxx, и запустить ну очень жирную прошивку в нативном режиме - с поддержкой отладки. А на новых чипах от st этот режим уже часть периферии - исполняется самостоятельно, без ручных бутов.
  2. Освоение ARM контроллеров

    Цитата(maxntf @ Mar 30 2016, 16:05) Понятно что нужно детально изучать все доки. Но вначале нужно иметь грубое поверхностное представление. Поиграйтесь кубиком от st, там есть все варианты, в том числе и уже готовые проекты для печаток от st - со всеми используемыми ногами (смотрите на свободные - они вам доступны). http://www.st.com/web/catalog/tools/FM147/...2?sc=stm32cube#
  3. Cortex и гонки при сне

    Цитата(ataradov @ Mar 30 2016, 15:23) Разумный совет как всегда нашелся на англоязычном форуме. А как оно выглядит-то? ваше англоязычное решение. Цитата(jcxz @ Mar 30 2016, 14:41) Не понимаю - Вы чего доказать-то пытаетесь? Чистый новый проект, три прерывания от кнопок с разными уровнями 2, 3, 4. Жму 4, запрет прерываний и цикл, жму 2 ,3 , Выхожу из цикла, снимается запрет - попадаю в 2 ( нормально), Выхожу из цикла 2 - попадаю в 4 и майн. Без запрета прерываний - попасть в 3 можно. Наверное я что-то делаю не так, может у меня камень с дефектом, но команда __disable_irq(); - мне не нравится.
  4. Cortex и гонки при сне

    Цитата(jcxz @ Mar 30 2016, 12:32) Бред! При запрете прерываний они не теряются, а копятся в регистре запросов ожидающих прерываний. Как только прерывания будут разрешены, будет выбрано одно из ожидающих прерываний с наивысшим приоритетом и перейдёт в стадию обслуживания. Действительно бред, записать в один регистр сразу кучу прерываний. Вложенность прерываний организованна по подобию стека. Соответственно в один момент может быть доступно всего одно активное прерывание, при запрете оно и регистрируется. В момент регистрации определяется как будет осуществятся возврат из него. Для разных состояний ядра arm - это разные точки восстановления, их всего 4 штуки. Дык вот, в момент действующего прерывания - этот адрес поддержки ядра уже использован. По заложенному сценарию после снятия запрета - можно будет выполнить одно дополнительное вложенное прерывание. Потому-что невозможно прописать адрес возврата для прерывания которое ещё не исполнилось, но имеет иной уровень приоритета. Отсебятина в регистре возврата прерывания в режиме ос - типа 0xFFFFFFFD - это и есть указатель на этот регистр. Это значение lr пишется в стек при вложенном новом прерывании более высокого уровня. Всё пля, стек прерываний закрыт. Напомню - в ос вся система крутится на самом слабом прерывании. Это сделано для того чтобы всё содержимое стека прерываний было выгружено, и состоялся переход на стек потока. Время отведённое для определения приоритета прерывания, а так-же установки адреса для чтения вектора - равно одному такту. Там просто нет возможности сравнивать все 15 уровней. Аппаратная возможность сравнения приоритета работает только в одну сторону - между действующим прерыванием и новым/отложенным более низким. Сравнить отложенное более высокое с новым низким отложенным - просто невозможно.
  5. Cortex и гонки при сне

    Цитата(GetSmart @ Mar 30 2016, 08:59) Что за источник это утверждает? Глобальный запрет прерываний флагом I регистра CPSR/PSR должен только запрещать их исполнение. Именно так. В дополнение - изначально Base priority mask register содержит 8 бит для определения приоритета, хотя в Cortex используется только 4 бита. При новом прерывании с более высоким уровнем внутри уже работающего - выставляется признак вложенного прерывания в Priority mask register. Это для управления возвратом из нового прерывания. При этом сравнение уровня прерывания происходит в момент его события. При запрете прерываний - и возникновении двух и более новых прерываний с разными уровнями - разрулить конечное состояние уже не получится. По этому запоминается первая регистрация нового прерывания, а всё остальное - игнорируется. В доках инфа на эту тему очень смутная. Проще проверить практически.
  6. Cortex и гонки при сне

    Цитата(jcxz @ Mar 29 2016, 19:13) Что там велосипедить? Запрет прерываний CPSID I - это и есть большой глабля. Подобные грабли есть практически во всех мобильных ОС "реального времени". Но прикол в том что при запрете прерываний - перестаёт создаваться очередь этих самых прерываний согласно приоритетам, то-есть банально теряются прерывания. Шанс маленький, да и поймать его достаточно сложно - но сам факт накладывает ограничения на реальность. В идеале ос должна быть без запретов прерываний, а такой финт можно реализовать только через SVC. Цитата(jcxz @ Mar 29 2016, 15:22) А если Вы собираетесь возбуждать SVC внутри ISR аппаратного прерывания - это невозможно, ибо SVC - синхронное прерывание, это не PendSV, в ISR SVC будет вход сразу же, без ожидания выхода из ISR аппаратного прерывания, и последующие аппаратные прерывания будут заблокированы. Попытаетесь запретить - получите HardFault. Без запретов прерываний - вызов SVC возможен из любого места, в любом режиме работы ядра. Живая очередь прерываний по приоритетам будет продолжать создаваться в фоне, без какого-либо лага. Собственно моя ос - http://forum.ixbt.com/topic.cgi?id=48:11735 репозиторий https://bitbucket.org/AVI-crak/rtos-cortex-m3-gcc/commits/ Тот самый кусок кода - который отправляет ядро в сон по условию единственной оставшийся в конвертере нулевой задачи, когда в нулевой нет задач на обработку. То-есть момент когда чип сделал всё что от него требуется, и ожидает внешнего события. КодsTask_nil_re:             ldr     r5, [r12, #12]          // адрес задач на обработку памяти             cbnz    r5, sTask_nil_nw             ldr     r0, [r12]             ldr     r1, [r0]             cmp     r0, r1                  // активная единственная нулевая             ittt    ne                       // то ждём физики             movne   r3, 0x10             svcne   0x0                     // __switch 0x10             bne     sTask_nil_re             wfi             b       sTask_nil_re sTask_nil_nw: В линейном коде без ос - достаточно языка С. do { __WFI(); } while(флаг);
  7. Cortex и гонки при сне

    Цитата(ataradov @ Mar 29 2016, 00:12) Что я пропустил? Как правильно обрабатывать такие ситуации? Само понятие сна - это ожидание прерывания без работы ядра мк. Допустим в коде без ос: прерывание связанное с точкой останова сбрасывает бинарный флаг, в точке сна в цикле проверяется флаг - профит, спим лишнее время. do { __WFI(); }while(флаг); сначала спим, а потом проверяем. В коде с ос всё немного сложнее. Тут простой запрет прерываний применять нельзя, их необходимо выключать по одному - в момент когда они полностью отработали. Иначе получится банальный сбой программы. Ведь прерывание по сути - это отложенное событие. После - все задачи должны быть переведены в зависимость от главного потока (вытолкнуть из диспетчера в ожидание). Ну а сам основной поток - просто обязан "переключаться диспетчером в холостом режиме", но теперь он будет всё время находится в бесконечном цикле проверки флага от важного внешнего прерывания ( его есно нужно оставить). Всё это происходит очень быстро, а паузы между активностью просто громадные. МК спит, хотя это и не 100% сон, получается где-то 99,99% от номинала.
  8. STM32F407VET6 DMA Каналы и потоки

    Цитата(nanorobot @ Mar 23 2016, 09:05) Вот такая фегня от ST. Неужели так сложно расставить запятые? смысл сообщения меняется - казнить нельзя миловать. DMAx * DMAx_Stream * 8 = 16. И для таких случаев проще написать собственную библиотеку дма один раз, и больше не парится с кубиками и разными чипами.
  9. STM32F407VET6 DMA Каналы и потоки

    Цитата(SpyBot @ Mar 23 2016, 04:19) Так один поток содержит 8 каналов. В разных потоках пусть и с одинаковым номером канала вполне дма будет работать. DMA STM32F407 Ага, записать в один регистр (например DMA2_Stream0 -> CR) - два разных номера канала.
  10. Цитата(scifi @ Mar 4 2016, 21:51) Это что-то новенькое Да. См. тут. А тут значится ложная инфа ? https://www.arm.com/products/processors/cla...arm9/arm926.php И тут. https://www.arm.com/products/processors/cla...arm9/arm926.php, заявлена двоичная совместимость с ядром ARM7TDMI.
  11. Цитата(Himmler @ Mar 3 2016, 23:38) Сегодня начал мерить производительность кода и познакомился с кучей неприятных сюрпризов архитектуры ARM. Это наверное ваша команда чтения из памяти виновата LDRB R3, [R6, R0, LSR #24] У старенького arm926 - ядро ARM7TDMI, и его команды имеют чёткое описание http://www.gaw.ru/html.cgi/txt/doc/micros/...tmi/insruct.htm Формат чтения памяти : [Rn, +/-Rm, LSR #5bit_shift_imm] , но в реальности LSR-LSL - это пятый бит смещения, а нулевой бит просто не участвует в операции - и того 3 бита смещения. То-есть как у всех ARM чипов.
  12. LDRB R3, [R6, R0, LSR #24] - это наверное из другой вселенной. В скобках адрес, при этом модификации подвергается последний регистор в записи, и двигать (умножать) его можно исключительно в лево, и число для модификации от единицы до трёх, и чтение байта с такой модификацией - теряет смысл, ибо глюканёт на несоответствии объявленных границ выравнивания переменных и зарегистрированной командой. В целом трешь и угар, выдыхайте.
  13. Не понимаю как у вас получается 9 команд, и 18 в уме. У меня получилось 20 команд, и 35 системных тиков. Код        // Cortex-M3         // r0  вход-выход             push   {r1, r2, r3, r4, r5, lr}         ldr     r0, =входное         ldr     r1, =адрес таблиц (1+2+3+4)         mov     r2, #0xFF                   // маска         and     r3, r0, r2         ldrb    r4, [r1, r3]                // первый байт         and     r3, r2, r0, lsr #8         add     r0, r0, #0x100         ldrb    r5, [r0, r3]                // второй байт         add     r0, r0, #0x100         and     r3, r2, r0, lsr #16         add     r4, r4, r5, lsl #8         ldrb    r5, [r0, r3]                // третий байт         add     r0, r0, #0x100         lsr     r0, r0, #24         add     r4, r4, r5, lsl #16         ldrb    r5, [r0, r3]                // последний байт         add     r0, r4, r5, lsl #24         pop     {r1, r2, r3, r4, r5, lr} Можно ещё читать байт прямо в разряды регистра, но без выравнивания таблиц - может получиться кака.
  14. Формирование int из массива char

    Даже в случае безумного С кода, на асме получается необходимый минимум. В даже если проц не может читать/писать не выровненное - этот кусок он обязан выполнить. Код    ldr      r1, =адрес_char     mov     r3, #0     ldrb    r0, [r1], #4     add     r3, r3, r0,     ldrb    r0, [r1], #4     add     r3, r3, r0, lsl #8     ldrb    r0, [r1], #4     add     r3, r3, r0, lsl #16     ldrb    r0, [r1], #4     add     r3, r3, r0, lsl #24     ldr     r1, =адрес_uint32_t     str     r3, [r1]
  15. Формирование int из массива char

    Цитата(AlexeyT @ Feb 12 2016, 22:32) В каком именно месте происходит зависание, сказать не могу, процессор - 1986ВЕ1Т, там с дебагом туго. Заставили? Наверное проблема в том что промежуточные значения сохраняются в память,вместо того чтобы висеть в регистрах. Хотя для этого ну уж очень сильно постараться нужно, например объявить несколько глобальных переменных в регистрах мк - и превратить чип в реальный тормоз. Решение в лоб - переменная uint32_t - для промежуточных вычислений. И кстати, int - число со знаком равное размеру регистра мк, в этом случае с переносимостью кода будут проблемы, а так-же с простейшим сложением чисел без знака. На С можно любую ересть написать без юзанья int - и этот код будет выполняться на любом процессоре с одинаковым результатом.
  16. Изменение состояния GPIO (stm32l)

    Цитата(Den5 @ Jan 21 2016, 19:57) Приходится отлаживать шкаф с реле, во время перепрошивки выводы оказываются в 3 состоянии и происходит дикое переключение релюшек. Пока не попали на многомиллионный счётчик - переделывайте печатку с мк. Перепрошивка через варт с оптической развязкой, защита всего что смотрит во внешний мир, и так далее. Все важные управляющие ноги должны работать через логику - прохождение сигнала через неё только при особой комбинации состояний на ногах мк. Такой - что не в состоянии возникнуть при переходных процессах мк, и в случае выхода его из строя.
  17. Цитата(Tarbal @ Jan 25 2016, 09:55) Я сгенерировал кубом код для STM32F429 и добавляю в него необходимые мне функции. В этом и есть основная проблема. Код для прерывания необходимо писать самому, с минимальным использованием внешних данных. Сами функции в такой системе делятся на два типа - имеющие зависимости и без них. В случае когда в функции есть хотя-бы одна внутренняя или внешняя статическая переменная - последняя считается зависимой. У такой функции есть ограничения при работе в составе ос, и на использование последней в прерываниях. Точнее: применять можно - но только в одном месте. Функции без зависимостей - можно применять бесконечное количество раз одновременно, в том числе и в прерываниях. И неважно сколько у неё входных/выходных параметров, и сколько она в себе несёт вторичных вызовов. Всё аккуратно посчитается и вернётся на свои места. Так-что считаю ошибкой сам код прерывания, а не грабли вокруг него.
  18. STM32: Синхронизация таймеров

    Цитата(Haamu @ Jan 23 2016, 23:04) Собственно вопрос в том, как так по хитрому настроить срабатывание таймеров, чтобы сделать всё этом максимально синхронно? Ну, в случае если запуск точности не требует - то можно. Весь смысл - не вылезать из прерывания, а лишь переходить из одного - в другое. Код прерывания разместить в памяти. Не в курсе - но если есть CCRAM - то только там. Только таким способом можно быть 100% уверенным в нулевой латентности событий.
  19. Цитата(ветерок @ Jan 9 2016, 03:24) требуется написать код 4 канального вольтметра с записью на SD карту лучше STM32, нужно по-бодрее АЦП Для начала нужно подумать, чего потом с этими данными делать. Даже не подумать, а просто проверить возможность продуктивной работы с таким массивом данных. Создать на компе очень жирный файл, 64гиг и выше, по желаемому формату. И попытаться с ним работать. Очень быстро придёт понимание, что 99,99% содержимого - вода. Создать файл можно за десять минут, - проверка для вас ничего не стоит.
  20. Цитата(VHEMaster @ Dec 24 2015, 22:05) почему-то нельзя просмотреть содержимое SDRAM через отладчик... Это и есть ответ, сбой инициализации sdram. В нормальном состоянии вся область sdram прекрасно читается отладчиком.
  21. Cortex-M7

    Всё верно, 4 бакса на печатку и мелочь, и бакс на чип - это ещё с маржой логистики-продажи. Здесь чип имеет предварительный заказ на фабрике в миллионных количествах: хорошо спланированный, самый дешёвый вариант из всех возможных. По этой причине кремниевая фабрика выставила настолько низкий ценник, что даже после двух-трёхкратного умножения для пользователя ценник останется в пределах бакса. Кстати фирма очень сильно рискует. В случае провала она останется должна производителю кристаллов даже если эти чипы не будут вывезены с фабрики - денежку придётся отдавать, ибо договор's. Гораздо чаще бывает иная ситуация. Готовый отлаженный чип резко кидают в массовое производство. Менеджеры требуют кровь из носу - моментальное изготовление, чтобы так-же быстро скинуть в рынок и возможно - исчезнуть. Именно на таких заказчиках кремниевая фабрика расширяется в буквальном смысле этого слова - покупает новое оборудование, строит новые помещения и так далее. Любой бзык за деньги клиента.
  22. embedded cron

    Цитата(evgen2 @ Dec 2 2015, 17:32) Почему невозможно? Просыпаемся по RTC, смотрим, какие есть "задачи", если нет - то спим дальше, если есть - выполняем их - последовательно - типа дрыгнуть ногами, запустить АПЦ и дождаться результата (т.е. квазиодновременно, если у нас минимальный квант от RTC секунда), перед тем как заснуть пробегаемся по будильникам, находим ближайший, программируем время следующего прерывания RTC и засыпаем. RTC позволяет (более лучше спать и) меньше потреблять, чем программный/нутряной таймер. Да вот фига. Просыпаемся когда уже пора что-то делать, потому как будильник на это время взведён. Иначе смысл в будильнике отпадает, можно на программных таймерах считать, с точностью в миллисекунды. Завёл одну переменную в 64 бита - и железяка её за всю твою жизнь не обнулит.
  23. embedded cron

    Цитата(evgen2 @ Dec 2 2015, 15:11) ну да, как-то так мыслится/хочется, только с функцией "периодический будильник" (раз в N секунд включаться на M секунд) и обработкой ситуации "несколько будильников сработали одновременно". Это невозможно на физическом уровне. Ваш мк будет управлять физикой с двумя состояниями - вкл-выкл, ну может быть ещё шим - но у него тоже пишется единственное значение. Значит все эти глюки необходимо разрулить ещё до фактической установки будильника. Функция - будильник каждую секунду - задаётся с некорректными значениями неиспользуемых разрядов будильника. Например каждую секунду - число секунд, а минуты, часы дни - года FFFF. Тогда при установке будильника можно будет задействовать отдельный канал со спец режимом, именно для этих целей, но таких каналов кажись всего один штук. Ну и управление физикой будет очень ограниченным. С этим делом прекрасно справляется программный таймер, там даже ничего изобретать не нужно.
  24. embedded cron

    Кхм, RTC имеет ограниченное количество будильников. При попытке в наглую сделать 10 будильников с разным временем и последовательностью установки - вас ждёт жестокий облом. Тут требуется собственный диспетчер RTC, который будет знать о всех активных будильниках, и устанавливать их по порядку даты. Это можно и без ос сделать, но максимальное количество будильников должно быть ограниченно известным вам числом. Проснулись, прошлись по всем будильникам и нашли минимальное время в + от текущего, установили , далее обработка функции на текущее время, и сон. Добавление будильника - смотрим записи с датой ниже текущей, и юзаем первую-же попавшуюся. Проект собирается без ос, любыми доступными способами.
  25. Цитата(Олег Гаврильченко @ Nov 25 2015, 14:37) Это происходит после того как питание сначала сняли, а затем опять включили через короткое время. PWR Расширенная система контроля и управления питанием. Скорей всего срабатывает контроль на понижение напряжения лапы PVD, но при этом нету барьера из двух встречных диодов между аналоговым питанием и силовым. В результате либо аналог либо сила начинает сбоить раньше чем сработает датчик на PVD.