|
|
  |
Написал порт scmRTOS под ARM, интересны отзывы |
|
|
|
May 19 2006, 13:32
|

Гуру
     
Группа: Свой
Сообщений: 13 372
Регистрация: 27-11-04
Из: Riga, Latvia
Пользователь №: 1 244

|
Цитата(Сергей Борщ @ May 19 2006, 16:13)  Если есть желание можем сравнивать. Жду предложений. Надо будет заняться безотносительно к scmRTOS, правда со временем похоже будет изрядно туго, когда на работу выберусь. Быстро не обещаю. Ну а быстренько и Вашими руками, то можно быстренько вместо ОТСУТСТВУЕЩЕГО во FreeRTOS семафора сваять аналогичную моргалку на банальном флаге - это просто даст заметно более приближенную к реальной оценку именно шедулера и переключателя задач.
--------------------
Feci, quod potui, faciant meliora potentes
|
|
|
|
|
May 19 2006, 13:37
|

Гуру
     
Группа: Модераторы
Сообщений: 8 455
Регистрация: 15-05-06
Из: Рига, Латвия
Пользователь №: 17 095

|
Цитата(zltigo @ May 19 2006, 16:32)  Цитата(Сергей Борщ @ May 19 2006, 16:13)  Если есть желание можем сравнивать. Жду предложений.
Ну а быстренько и Вашими руками, то можно быстренько вместо ОТСУТСТВУЕЩЕГО во FreeRTOS семафора сваять аналогичную моргалку на банальном флаге Или что-то недопонял или в FreeRTOS флагов тоже не нашел. Можно хотябы в общих словах пример кода, я его погоняю.
--------------------
На любой вопрос даю любой ответ"Write code that is guaranteed to work, not code that doesn’t seem to break" ( C++ FAQ)
|
|
|
|
|
May 20 2006, 14:01
|
Профессионал
    
Группа: Свой
Сообщений: 1 481
Регистрация: 10-04-05
Пользователь №: 4 007

|
Я давно приглядываюсь к scmRTOS применительно к ARM. На работе текучка одолела – совершенно невозможно заняться чем-то впрок.
Но есть соображение насчет скорости работы scheduler’а. Поиск текущей приоритетной задачи осуществляется простым перебором бит в слове состояния процессов. Очевидно, что время поиска прямо пропрционально номеру приоритета, что не есть хорошо. Есть классная функция, оптимизированная для ARM, которая выдает номер младшего установленного бита в 32-разрядном слове (она используется в Linux’e и TNKernel). Вот ее текст: ffs_asm:
;-- Standard trick to isolate bottom bit in r0 or 0 if r0 = 0 on entry rsb r1, r0, #0 ands r0, r0, r1
;-- now r0 has at most one set bit, call this X ;-- if X = 0, all further instructions are skipped
adrne r2, .L_ffs_table orrne r0, r0, r0, lsl #4 ; r0 = X * 0x11 orrne r0, r0, r0, lsl #6 ; r0 = X * 0x451 rsbne r0, r0, r0, lsl #16 ; r0 = X * 0x0450fbaf
;-- now lookup in table indexed on top 6 bits of r0 ldrneb r0, [ r2, r0, lsr #26 ] bx lr
.L_ffs_table: ;-- 0 1 2 3 4 5 6 7 .data.b 0, 1, 2, 13, 3, 7, 0, 14 ; 0- 7 .data.b 4, 0, 8, 0, 0, 0, 0, 15 ; 8-15 .data.b 11, 5, 0, 0, 9, 0, 0, 26 ; 16-23 .data.b 0, 0, 0, 0, 0, 22, 28, 16 ; 24-31 .data.b 32, 12, 6, 0, 0, 0, 0, 0 ; 32-39 .data.b 10, 0, 0, 25, 0, 0, 21, 27 ; 40-47 .data.b 31, 0, 0, 0, 0, 24, 0, 20 ; 48-55 .data.b 30, 0, 23, 19, 29, 18, 17, 0 ; 56-63 Очевидно имеем констатное время поиска номера младшего установленного бита в слове.
Думаю полезно эту функцию использовать вместо стандартного решения.
|
|
|
|
|
May 20 2006, 15:32
|
Профессионал
    
Группа: Свой
Сообщений: 1 481
Регистрация: 10-04-05
Пользователь №: 4 007

|
Да. Еще про critical section. Твой вариант запрета/разрешения прерываний не очень безопасный вариант (см. Atmel Application Note Rev. 1156A–08/98) и лучше это сделать так, как сделано в UCOS порте для ARM: ;------------------------------------------------------------------------------ ;- Function : unsigned int EnterCritical(void) ;- Treatments : Secure Disable All Interrupt (Atmel rev.1156A) and ; return irq status for disable interrupt ;------------------------------------------------------------------------------ EXPORT EnterCritical
EnterCritical PROC MRS r0,CPSR ; Set IRQ and FIQ bits in CPSR to disable all interrupts ORR r1,r0,#NO_INT MSR CPSR_c,r1 MRS r1,CPSR ; Confirm that CPSR contains the proper interrupt disable flags AND r1,r1,#NO_INT CMP r1,#NO_INT BNE EnterCritical ; Not properly disabled (try again) mov pc, lr ; return in R0 - saved interrupt status
;------------------------------------------------------------------------------ ;- Function : void ExitCritical(unsigned int IrqStatus) ;- Treatments : restore irq status, saved by function EnterCritical() (Atmel rev.1156A) ;------------------------------------------------------------------------------ EXPORT ExitCritical
ExitCritical PROC MSR CPSR_c, r0 mov pc, lr
Работает дольше, но безопаснее
|
|
|
|
|
May 20 2006, 17:50
|

Гуру
     
Группа: Модераторы
Сообщений: 8 455
Регистрация: 15-05-06
Из: Рига, Латвия
Пользователь №: 17 095

|
Цитата(sergeeff @ May 20 2006, 17:01)  Я давно приглядываюсь к scmRTOS применительно к ARM. На работе текучка одолела – совершенно невозможно заняться чем-то впрок.
Но есть соображение насчет скорости работы scheduler’а. Поиск текущей приоритетной задачи осуществляется простым перебором бит в слове состояния процессов. Очевидно, что время поиска прямо пропрционально номеру приоритета, что не есть хорошо. Есть классная функция, оптимизированная для ARM, которая выдает номер младшего установленного бита в 32-разрядном слове (она используется в Linux’e и TNKernel). Вот ее текст: Думаю полезно эту функцию использовать вместо стандартного решения. Отлично! Гарри как раз спрашивал, если такая аппаратная функция в ARM. Обязательно добавлю. Цитата(ig_z @ May 20 2006, 18:01)  Посмотрел ваш порт, сходу возник архитектурный вопрос. Почему для контекст свитчера вы выбрали ВИК-СВ а не просто СВИ, были какие то особые причины? СВИ - ядерная часть и поэтому есть у всех, а ВИК - периферия, имеет право и не быть в кристалле. Дело в том, что SWI всем хороша кроме одного - она исполняется независимо от того - разрешены прерывания или нет. Когда переключение вызывается из потока проблем нет, а вот когда из прерывания возникают сложности - обработчик прерывания уже наложил в стек своей информации. Идеология scmRTOS предполагает, что при возникновении необходимости переключения контекста внутри обработчика прерывания взводится запрос на переключение а собственно прерывание переключателя вызывается в момент выхода из обработчика, когда разрешаются глобальные прерывания и стек содержит только данные текущего потока. Я подумывал о использовании SWI при вызове из потока и "честного" прерывания при переключении в обработчике прерывания, но это потребовало бы изменения "непортируемой" части ОС, хотя и ускорило бы переключение. В общем я пока в раздумье. Есть идеи? Цитата(sergeeff @ May 20 2006, 18:32)  Да. Еще про critical section. Твой вариант запрета/разрешения прерываний не очень безопасный вариант (см. Atmel Application Note Rev. 1156A–08/98) и лучше это сделать так, как сделано в UCOS порте для ARM: ........... Работает дольше, но безопаснее Спасибо, не знал (только начинаю ARM осваивать). Изучу и учту. Собственно ради таких замечаний и открыл это обсуждение.
Сообщение отредактировал Сергей Борщ - May 20 2006, 17:52
--------------------
На любой вопрос даю любой ответ"Write code that is guaranteed to work, not code that doesn’t seem to break" ( C++ FAQ)
|
|
|
|
|
May 21 2006, 00:02
|
Местный
  
Группа: Свой
Сообщений: 437
Регистрация: 27-08-04
Пользователь №: 551

|
Цитата(Сергей Борщ @ May 20 2006, 20:50)  Цитата(ig_z @ May 20 2006, 18:01)  Посмотрел ваш порт, сходу возник архитектурный вопрос. Почему для контекст свитчера вы выбрали ВИК-СВ а не просто СВИ, были какие то особые причины? СВИ - ядерная часть и поэтому есть у всех, а ВИК - периферия, имеет право и не быть в кристалле.
Дело в том, что SWI всем хороша кроме одного - она исполняется независимо от того - разрешены прерывания или нет. Когда переключение вызывается из потока проблем нет, а вот когда из прерывания возникают сложности - обработчик прерывания уже наложил в стек своей информации. Идеология scmRTOS предполагает, что при возникновении необходимости переключения контекста внутри обработчика прерывания взводится запрос на переключение а собственно прерывание переключателя вызывается в момент выхода из обработчика, когда разрешаются глобальные прерывания и стек содержит только данные текущего потока. Я подумывал о использовании SWI при вызове из потока и "честного" прерывания при переключении в обработчике прерывания, но это потребовало бы изменения "непортируемой" части ОС, хотя и ускорило бы переключение. В общем я пока в раздумье. Есть идеи? Если я правильно понимаю - SWI имеет 6-й наинизший приоритет, поэтому не может прерывать FIQ (3) IRQ (4). Иначе вообще не понятно, зачем нужны софт прерывания. Цитата(Сергей Борщ @ May 20 2006, 20:50)  Цитата(sergeeff @ May 20 2006, 18:32)  Да. Еще про critical section. Твой вариант запрета/разрешения прерываний не очень безопасный вариант (см. Atmel Application Note Rev. 1156A–08/98) и лучше это сделать так, как сделано в UCOS порте для ARM: ........... Работает дольше, но безопаснее
Спасибо, не знал (только начинаю ARM осваивать). Изучу и учту. Собственно ради таких замечаний и открыл это обсуждение. Возможно достаточно использовать интринсики __disable_interrupt __enable_interrupt. Соответствуют рекомендациям АРМ. Но они вроде бы не инлайнятся.
|
|
|
|
|
May 21 2006, 12:07
|
Местный
  
Группа: Свой
Сообщений: 251
Регистрация: 23-06-04
Пользователь №: 154

|
Цитата(ig_z @ May 20 2006, 18:01)  Почему для контекст свитчера вы выбрали ВИК-СВ а не просто СВИ, были какие то особые причины? СВИ - ядерная часть и поэтому есть у всех, а ВИК - периферия, имеет право и не быть в кристалле. Если я правильно понимаю - SWI имеет 6-й наинизший приоритет, поэтому не может прерывать FIQ (3) IRQ (4). Иначе вообще не понятно, зачем нужны софт прерывания. SWI единственный коректный способ вызова SYSTEM (protected) режима или функций от USER режима.
|
|
|
|
|
May 21 2006, 12:36
|
.
     
Группа: Участник
Сообщений: 4 005
Регистрация: 3-05-06
Из: Россия
Пользователь №: 16 753

|
Цитата SWI единственный коректный способ вызова SYSTEM (protected) режима или функций от USER режима. Можно узнать почему? _____________________ Кстати, если откуда-то вызывается критическая секция, то смысла её вызывать из USER нет никакого. Всё-равно прерывания не запретятся. Именно на этот счёт так усложнилась процедура их запрещения. Хотя пользы от неё почти никакой. Сразу задача зависнет. Цитата Возможно достаточно использовать интринсики __disable_interrupt __enable_interrupt. Соответствуют рекомендациям АРМ. Но они вроде бы не инлайнятся. Не инлайнятся потому, что работают только а ARM-режиме и чтобы их выполнить из THUMB нужно вызвать ARM-процедуру (__disable_interrupt) и вернуться обратно. __disable_interrupt тоже завесит задачу если её вызвать из USER. Хотя если... если очень постараться, то можно. Можно запрещать прерывания USER-режима переключаясь в SYSTEM, а потом обратно. Например через тот же SWI. Но это будет ещё медленней (немного).
Сообщение отредактировал GetSmart - May 21 2006, 12:31
--------------------
Заблуждаться - Ваше законное право :-)
|
|
|
|
|
May 21 2006, 16:54
|

Гуру
     
Группа: Свой
Сообщений: 13 372
Регистрация: 27-11-04
Из: Riga, Latvia
Пользователь №: 1 244

|
Цитата Можно хотябы в общих словах пример кода, я его погоняю. Думаю сам все сделаю через недельку и доложу. Пока начал немножко ядрышко подчищать :-), в том числе в части critical section для ядра и для приложений. Цитата(GetSmart @ May 21 2006, 15:36)  Не инлайнятся потому, что работают только а ARM-режиме и.... C Thumb дело ясное, но IAR какое-то темноватое дело получается :-( __disable_interrupt() не инлайнится и в ARM mode, хотя должна. Цитата Возможно достаточно использовать интринсики __disable_interrupt Достаточно, в __disable_interrupt() именно такой код 'с контролем' и заложен, вопрос только в том, нужны-ли эти выкрутасы не для Atmel-овских чипов. Кроме того, не совсем ясно, нужны-ли эти выкрутасы не при одновременном запрещении IRQ и FIQ. Еще к размышлению - а почему в порте только IRQ запрещаются? Если использовать исключительно для использования в ядре, то можно подумать и о варианте (скорость?) блокировки только таймерного прерывания. Но тупое-полное для приложений тоже реализовано должно быть.
--------------------
Feci, quod potui, faciant meliora potentes
|
|
|
|
|
May 21 2006, 18:34
|

Гуру
     
Группа: Свой
Сообщений: 13 372
Регистрация: 27-11-04
Из: Riga, Latvia
Пользователь №: 1 244

|
Цитата(GetSmart @ May 21 2006, 20:38)  А причём тут Атмел? У других жалоб не встречал. Цитата Это "выкрутасы" для стандартного АРМ-ядра нужны. Я дважды натыкался на комментарии типа такого: Код mrs r0,CPSR orr r1,r0,#NOINT msr CPSR_c,r1 ;-- Atmel add-on mrs r1,CPSR ;-- Check CPSR for correct contents and r1,r1,#NOINT cmp r1,#NOINT bne tn_cpu_save_sr ;-- Not disabled - loop to try again ;-------- mov pc, lr Ссылка на источник от _ARM_ есть? Цитата Вышепроцитированная проверка делается только для USER-режима, в котором нельзя запрещать прерывания. О чем Вы это? Когда нельзя - тогда НЕЛЬЗЯ! А тут элементарный контроль на то, что флаги установились. Цитата но в этом порте как я понял FIQ вообще не используется и либо нужно придумать ещё одну особую критическую секцию, либо оставить всё на совести пользователя. А на переключение контекстов они вроде как не влияют. Ага, не влияют - я, например, из обработчика FIQ какой-нибудь семафорчик (Signal) дерну, который шедулер за собой потянет...
--------------------
Feci, quod potui, faciant meliora potentes
|
|
|
|
|
May 21 2006, 19:08
|
.
     
Группа: Участник
Сообщений: 4 005
Регистрация: 3-05-06
Из: Россия
Пользователь №: 16 753

|
Самая близкая по смыслу цитата из <arm7tdmi.pdf>: Цитата 3.9.5 IRQ The IRQ (Interrupt Request) exception is a normal interrupt caused by a LOW level on the nIRQ input. IRQ has a lower priority than FIQ and is masked out when a FIQ sequence is entered. It may be disabled at any time by setting the I bit in the CPSR, though this can only be done from a privileged (non-User) mode. - самый конец цитаты. Хотя весь файл напичкан ограничениями в USER-режиме. Вообще, все эти заморочки стоит учитывать если Ось (порт) будет выполняться в этом режиме. Если же нет, то и заморачиваться не стоит. Цитата О чем Вы это? Когда нельзя - тогда НЕЛЬЗЯ! Ну дак это же не убьёт процессор. Просто команда выполнится в холостую. Для этого и проверка, чтобы у USER-проги и желания такого не возникало. Чисто через SYSTEM. А иначе - "висеть вам вечно". Цитата Ага, не влияют - я, например, из обработчика FIQ какой-нибудь семафорчик (Signal) дерну, который шедулер за собой потянет... Я ведь написал - на совести пользователя. Хотя в FIQ делать что-то сложное и вызывать систему вообще не рекомендуется. Так, по-быстренькому обратиться к портам или переменным и назад.
Сообщение отредактировал GetSmart - May 21 2006, 19:14
--------------------
Заблуждаться - Ваше законное право :-)
|
|
|
|
|
  |
2 чел. читают эту тему (гостей: 2, скрытых пользователей: 0)
Пользователей: 0
|
|
|