|
scmRTOS холостой ход и системный таймер |
|
|
|
Jul 9 2011, 09:01
|
Знающий
   
Группа: Участник
Сообщений: 998
Регистрация: 27-08-08
Пользователь №: 39 850

|
Пролем с IAR AVR OCью (310) пока нет. По ходу возникают всякие вопросы. 1. Могут ли разные процессы без ущерба себе использоваться одни и те же глобальные константы, типа Код const char __flash cTrPr15[5] = {0x55,0x34,0x0a,0x41,0xd4}; 2. Можно ли в разных процессах использовать одну и ту же глобальную функцию, например Код unsigned char USART_Receive( void ) { .... }
Сообщение отредактировал Acvarif - Jul 9 2011, 09:01
|
|
|
|
|
Jul 9 2011, 11:08
|
Знающий
   
Группа: Участник
Сообщений: 998
Регистрация: 27-08-08
Пользователь №: 39 850

|
Цитата(ReAl @ Jul 9 2011, 12:45)  1. А почему нет? Даже не-константы можно, только во избежание гонок защищаться от записи во время других операций (других записей или других чтений). Понял. Спасибо. Наверное имеется ввиду Мутекс? Цитата 2. Если функция реентрабельна. Не все функции стандартной библиотеки реентрабелны, например, strtok() нельзя звать из двух процессов вперемешку. Спасибо. Пытаюсь до конца понять такую штуку: Если один процесс совершает омен по USATR0 и полученные данные помещает в глобальный массив типа A[25], то может ли другой процесс достать эти данные из этого же массива, выполнить с ними действия и дальше передать по USART1? Конечно имеется ввиду, что будет обеспечена блокировка совместного доступа через Мутекс. Если да, то получается, что к глобалам (в том числе и к глобальным функциям если они реентрабельны) в принципе имеют доступ все процессы? Тогда встает вопрос, зачем организовывать возможность передачи данных между процессами (например черех message) если все можно крутить через глобальные буфера? Например (могу шибаться) в QNX глобалы из процессов не доступны вообще.
Сообщение отредактировал Acvarif - Jul 9 2011, 11:10
|
|
|
|
|
Jul 9 2011, 11:57
|

Нечётный пользователь.
     
Группа: Свой
Сообщений: 2 033
Регистрация: 26-05-05
Из: Бровари, Україна
Пользователь №: 5 417

|
Конечно может. Цитата(Acvarif @ Jul 9 2011, 14:08)  Например (могу шибаться) в QNX глобалы из процессов не доступны вообще. Ну так (глобальный) объект message и является таким буфером. Только с дополнительным сервисом, чобы закат солнца вручную не организовывать. Цитата(Acvarif @ Jul 9 2011, 14:08)  Например (могу шибаться) в QNX глобалы из процессов не доступны вообще. Интересно, как они могут на уровне ОС запретить то, что компилятор разрешает :-) Другое дело, что они могут «не рекомендовать» такое использование. но сделать невозможным -- никак.
--------------------
Ну, я пошёл… Если что – звоните…
|
|
|
|
|
Jul 11 2011, 17:25
|
Знающий
   
Группа: Участник
Сообщений: 998
Регистрация: 27-08-08
Пользователь №: 39 850

|
Цитата(ReAl @ Jul 9 2011, 14:57)  Интересно, как они могут на уровне ОС запретить то, что компилятор разрешает :-) Другое дело, что они могут «не рекомендовать» такое использование. но сделать невозможным -- никак. Тоже так думал. Но оказывается так таки оно и есть. Потому, как в Linux (в том числе и Windows) и т. п. процессы это разные приложения у каждого из которых своя область видимости. Это по сути разные программы, типа PCAD и Word. В sсmRTOS процессы это потоки запущенные из одного места (не понимаю почему их назвали процессами). А у потоков область видимости на глобалы одна и та же. Поэтому все процессы (потоки) имеют достум ко всему, что объявлено перед main. Если что не так поправьте меня. Ну да ладно... это все не главное. Главное, что потоки работают неплохо. 1. Один из них по прерываниям T1 передает в PC данные по USART1 2. Другой, асинхронно с первым, проспав нужне количество тиков T0 (0.5 sec) формирует запрос по Modbus (Usart0). 3. Третий по прерываниям принимает и обрабатывает данные от Modbus (формирует массив для передачи в первый процесс). Первый данные должен будет передать в PC. Вот только пока не уяснил как лучше передать даные из 3 в 1 - через глобальный буфер или методом типа meccage? Как лучше?
Сообщение отредактировал Acvarif - Jul 11 2011, 17:26
|
|
|
|
|
Jul 12 2011, 13:46
|
Знающий
   
Группа: Участник
Сообщений: 998
Регистрация: 27-08-08
Пользователь №: 39 850

|
Цитата(dxp @ Jul 12 2011, 13:23)  А почему они потоки, а не процессы? Думаю потому, что у потока область видимости, например на глобалы одна и та же. Потоки могут работать с глобалами без особых проблем. В ОСях процессы это обычно отдельные приложения (в каждом из них можно запускать сколько угодно, в разумных пределах, потоков). Могу ошибаться...
|
|
|
|
|
Jul 12 2011, 13:56
|

Беспросветный оптимист
     
Группа: Свой
Сообщений: 4 640
Регистрация: 26-12-07
Из: Н.Новгород
Пользователь №: 33 646

|
Цитата(Acvarif @ Jul 12 2011, 17:46)  Думаю потому, что у потока область видимости, например на глобалы одна и та же. Потоки могут работать с глобалами без особых проблем. В ОСях процессы это обычно отдельные приложения (в каждом из них можно запускать сколько угодно, в разумных пределах, потоков). Могу ошибаться... Вообще-то не совсем так. Процессы или приложения - это сервисы, предоставляемые ОС. Потоки или нити - это механизмы, реализуемые непосредственно приложениями без участия операционки. В данном случае таски - это именно процессы, т.к. реализуются средствами оси. А вот если внутри процесса сделать хотя бы простецкую карусельку - это уже будут потоки.
--------------------
Программирование делится на системное и бессистемное. ©Моё :) — а для кого-то БГ — это Bill Gilbert =)
|
|
|
|
|
Jul 13 2011, 10:35
|
Знающий
   
Группа: Участник
Сообщений: 998
Регистрация: 27-08-08
Пользователь №: 39 850

|
Имеется три процесса. 1. Первый передача запросов Модбас (USART0) после спячки Sleep(900); Код // Передача команд по MODBUS template<> void TProc1::Exec() {
for(;;) { Sleep(900); // Запретить прием UCSR0B &= ~( 1 << RXEN0 ); // Запретить прерывания на прием USART0 UCSR0B &= ~(1<<RXCIE0); //--------------------------------------------------------------------------- ...... передача по USART0 типа // Ждять пока будет пуст буфер передачи while ( !(UCSR0A & (1<<UDRE0)) ); // Передача байта UDR0 = data;
//--------------------------------------------------------------------------- // Разрешить прием UCSR0B |= (1 << RXEN0); // Разрешить прерывания на прием USART0 UCSR0B |= (1<<RXCIE0); } } 2. Второй передача данных в PC (USART1) по прерыв. таймера 1 проспав Sleep(150); Код template<> void TProc2::Exec() { __watchdog_reset();
unsigned char i; for(;;) { // Ожидание Timer1_CompA через 90 мс Sleep(150); Timer1_CompA.Wait(); .... пердача типа while ( !(UCSR1A & (1<<UDRE1)) ); UDR1 = data; } } 3. Третий прием данных USART0 по прерываниям приема (заполнения приемного буфера) Код // Прием по Modbus template<> void TProc3::Exec() { for(;;) { // Sleep(1); // Сброс флага приема Usart0_rxc.Wait(); cRxBuf[cRxBufCount] = UDR0; cRxBufCount++; } } Сами прерывания Код //--------------------------------------------------------------------------- #pragma vector=TIMER1_COMPA_vect OS_INTERRUPT void Timer1_period_ISR() { OS::TISRW_SS ISRW;
ENABLE_NESTED_INTERRUPTS();
Timer1_CompA.SignalISR(); } //--------------------------------------------------------------------------- #pragma vector=USART0_RXC_vect OS_INTERRUPT void Usart0_rxc_ISR() { OS::TISRW_SS ISRW;
ENABLE_NESTED_INTERRUPTS();
Usart0_rxc.SignalISR(); } В таком виде все глохнет при попадании первых байт в приемный буфер USART0 Приоритеты процессов выставлены по очереди 1,2,3. Подскажите пожалуйста где я ошибаюсь?
|
|
|
|
|
Jul 13 2011, 13:00
|
Знающий
   
Группа: Участник
Сообщений: 998
Регистрация: 27-08-08
Пользователь №: 39 850

|
Цитата(AHTOXA @ Jul 13 2011, 15:15)  В прерывании Usart0_rxc_ISR() надо вычитывать UDR0, иначе не сбрасывается флаг прерывания:
Может всё же почитаете документацию на процессор, или вы собираетесь весь проект делать методом тыка с помощью конфы? Спасибо. Читал когда-то. Видно порядком подзабыл. Помогло, только без вложенных прерываний. Код #pragma vector=USART0_RXC_vect OS_INTERRUPT void Usart0_rxc_ISR() { OS::TISRW_SS ISRW;
cRxBuf[cRxBufCount] = UDR0; cRxBufCount++;
Usart0_rxc.SignalISR(); } Разве вычитывание UDR0 в процессе TProc3::Exec() это не то же самое? Процесс ждет прерывания (точнее Usart0_rxc.SignalISR())-> при его возникновении вычитывает UDR0, сбрасывается RXC0 -> процесс опять готов обработать прерывание. Разве не так? Или после обработки прерывания нужно обеспечить выход из процесса, переключиться куда нибудь? Здесь не врубаюсь...
|
|
|
|
|
Jul 13 2011, 17:43
|
Знающий
   
Группа: Участник
Сообщений: 998
Регистрация: 27-08-08
Пользователь №: 39 850

|
Цитата(Сергей Борщ @ Jul 13 2011, 16:42)  А как процесс получит управление, если вы в прерывании не сбросили RXC0? После выхода из обработчика процессор снова будет вызывать этот же обработчик. Спасибо Сергей. Уяснил. RXC0 нужно сбросить имено в прерывании чтением UDR0 (действительно мне нужно вспомнить матчасть). Это #pragma vector=TIMER1_COMPA_vect сам очищает свой флаг после выхода из обработчика. Там и переход в процесс (Timer1_CompA.Wait()  мягкий, без проблем. Если можно, еще один нюанс. Процесс 3 вызывается только если там имеется Sleep(>=1); Почему процесс не запускается просто по Usart0_rxc.SignalISR(); Usart0_rxc.Wait();
|
|
|
|
|
Jul 14 2011, 03:34
|

Adept
     
Группа: Свой
Сообщений: 3 469
Регистрация: 6-12-04
Из: Novosibirsk
Пользователь №: 1 343

|
Цитата(Acvarif @ Jul 12 2011, 20:46)  Думаю потому, что у потока область видимости, например на глобалы одна и та же. Потоки могут работать с глобалами без особых проблем. В ОСях процессы это обычно отдельные приложения (в каждом из них можно запускать сколько угодно, в разумных пределах, потоков). Могу ошибаться... Вы имеете в виду POSIX процессы? Ну, а причём тут они? У нас не POSIX система, а крохотная RTOS. Слово "процесс" обозначает некое продолжительное действие и употребляется в самых разных областях. По поводу терминологии в документации на v4 есть пара абзацев с аргументацией, почему выбран термин "процесс", а не "тред" и не "задача".
--------------------
«Отыщи всему начало, и ты многое поймёшь» К. Прутков
|
|
|
|
|
Jul 14 2011, 06:55
|
Знающий
   
Группа: Участник
Сообщений: 998
Регистрация: 27-08-08
Пользователь №: 39 850

|
Цитата(dxp @ Jul 14 2011, 06:34)  Вы имеете в виду POSIX процессы? Ну, а причём тут они? У нас не POSIX система, а крохотная RTOS. Слово "процесс" обозначает некое продолжительное действие и употребляется в самых разных областях. По поводу терминологии в документации на v4 есть пара абзацев с аргументацией, почему выбран термин "процесс", а не "тред" и не "задача". Да, нашел. Цитата О принятой терминологии. В scmRTOS используется термин «процесс» (process) для обозначения части программы, выполняемой циклически, самостоя- тельно и асинхронно по отношению к остальным частям программы. В литерату- ре и в терминологии, принятой в других ОСРВ для обозначения этого, часто ис- пользуются термины «задача» (task) и «тред» (thread – «нить», поток). Термин «процесс» был выбран сознательно, т.к. представляется, что он более удачно под- чёркивает смысл обозначаемого. Действительно, «задача» — понятие весьма широкое и может обозначать широкий спектр от школьной задачки по алгебре до боевой задачи роте спецназа. «Тред» — это дословно «нить», т.е. как видно из названия, это нечто такое, что имеет характеристику линейности, а не цикличности. Учитывая вышеприведён- ные доводы, термин «процесс» представляется более удачным вариантом — дей- ствительно, смысл этого слова в явном виде отражает действие1, протяжённое во времени, с возможностью цикличности2 как отдельных составных частей процес- са, так и всего процесса в целом. Спасибо. Вопрос снят.
Сообщение отредактировал Acvarif - Jul 14 2011, 06:56
|
|
|
|
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|