реклама на сайте
подробности

 
 
 
Reply to this topicStart new topic
> ucos+nios+isr, Работа с прерываниями в UCOS
Slaven
сообщение Sep 15 2014, 19:15
Сообщение #1





Группа: Участник
Сообщений: 10
Регистрация: 16-08-13
Пользователь №: 77 949



Доброго времени суток.
Создаю в eclipse проект на основе примера hello usoc. В нем есть две задачи, которые попеременно выводят в консоль сообщения, все вроде бы просто и понятно. В моей процессорной системе (Nios) есть порт (input) PIO. Он настроен на генерацию прерываний по нажатию на кнопку на моем борде. Если говорить о "чистом " C коде, то как зарегистрировать прерывания и описать их обработчик мне известно (через ф-ию alt_irq_register() и т.д.). В примере hello usoc я так и сделал, вот пример кода:

#include <stdio.h>
#include "includes.h"
#include "system.h"
#include "altera_avalon_pio_regs.h"
//#include "altera_avalon_pio_regs.h"
/* Definition of Task Stacks */
#define TASK_STACKSIZE 2048
OS_STK task1_stk[TASK_STACKSIZE];
OS_STK task2_stk[TASK_STACKSIZE];

/* Definition of Task Priorities */

#define TASK1_PRIORITY 1
#define TASK2_PRIORITY 8
volatile int buttons=0;
int led=0;
static void button_isr( void * base, alt_u32 id )
{
buttons = IORD_ALTERA_AVALON_PIO_EDGE_CAP(base);
IOWR_ALTERA_AVALON_PIO_EDGE_CAP(base,0x3);
}


void task1(void* pdata)
{

while (1)
{
if (buttons != 0)
{
switch (buttons) {
case 1:
alt_printf("Нажата кнопка pb_left\n ");
if (led == 0x80||led==0x00 )
led = 0x01;
else
led = led << 1;
buttons = 0;
break;

case 2:
alt_printf("Нажата кнопка pb_right\n ");
if (led == 0x01 ||led==0x00 )
led = 0x80;
else
led = led >> 1;
buttons = 0;
break;

default:
buttons = 0;
break;
}
IOWR_ALTERA_AVALON_PIO_DATA(LED_BASE,led);
}
printf("Hello from task1\n");
//OSTimeDlyHMSM(0, 0, 1, 0);
}
}
void task2(void* pdata)
{
while (1)
{
alt_irq_register(BUTTONS_IRQ, (void*)BUTTONS_BASE, button_isr);
printf("Hello from task2\n");
//OSTimeDlyHMSM(0, 0, 1, 0);
}
}
/* The main function creates two task and starts multi-tasking */
int main(void)
{
IOWR_ALTERA_AVALON_PIO_DATA(LED_BASE,0x00);
IOWR_ALTERA_AVALON_PIO_IRQ_MASK(BUTTONS_BASE, 0x3);
IOWR_ALTERA_AVALON_PIO_EDGE_CAP(BUTTONS_BASE, 0x3);
alt_irq_register(BUTTONS_IRQ, (void*)BUTTONS_BASE, button_isr);

OSTaskCreateExt(task1,
NULL,
(void *)&task1_stk[TASK_STACKSIZE-1],
TASK1_PRIORITY,
TASK1_PRIORITY,
task1_stk,
TASK_STACKSIZE,
NULL,
0);


OSTaskCreateExt(task2,
NULL,
(void *)&task2_stk[TASK_STACKSIZE-1],
TASK2_PRIORITY,
TASK2_PRIORITY,
task2_stk,
TASK_STACKSIZE,
NULL,
0);
OSStart();

return 0;
}

Но я чувствую, что в ucos такая работа с прерываниями некорректна.
Подскажите пожалуйста, какова идеология работы с прерываниями под ucos, и как должен выглядеть обработчик прерываний в моем случае, то есть описанный штатными средствами операционной системы?
Если есть возможность поделитесь простым примером, от которого можно оттолкнутся.
Go to the top of the page
 
+Quote Post
andrewlekar
сообщение Sep 16 2014, 10:53
Сообщение #2


Знающий
****

Группа: Участник
Сообщений: 837
Регистрация: 8-02-07
Пользователь №: 25 163



Обработчик как обработчик. Можете поллингом сделать:

while(1)
{
if(BUTTON_PRESSED()) ...
}

Будет и просто, и без volatile, и антидребезг заодно.
Go to the top of the page
 
+Quote Post
Slaven
сообщение Sep 16 2014, 17:10
Сообщение #3





Группа: Участник
Сообщений: 10
Регистрация: 16-08-13
Пользователь №: 77 949



Правильно ли я Вас понял, Вы предлагаете не использовать обработчик прерываний, а просто считывать состояние порта PIO?
Go to the top of the page
 
+Quote Post
andrewlekar
сообщение Sep 17 2014, 08:40
Сообщение #4


Знающий
****

Группа: Участник
Сообщений: 837
Регистрация: 8-02-07
Пользователь №: 25 163



Да.
Go to the top of the page
 
+Quote Post
Slaven
сообщение Sep 17 2014, 19:51
Сообщение #5





Группа: Участник
Сообщений: 10
Регистрация: 16-08-13
Пользователь №: 77 949



Тогда я Вас понял, такой вариант тоже возможен, но только меня интересует именно синтаксис описания прерывания штатными средствами OC, может кто-нибудь поделится опытом?
Go to the top of the page
 
+Quote Post
Lagman
сообщение Sep 18 2014, 11:41
Сообщение #6


Знающий
****

Группа: Свой
Сообщений: 875
Регистрация: 28-10-05
Пользователь №: 10 245



Цитата(Slaven @ Sep 17 2014, 23:51) *
Тогда я Вас понял, такой вариант тоже возможен, но только меня интересует именно синтаксис описания прерывания штатными средствами OC, может кто-нибудь поделится опытом?

Использовал на другом процессоре.
Нет там никаких штатных средств описания прерывания, есть только общие слова (ucos-ii)
Цитата
YourISR:
Save all CPU registers;
Call OSIntEnter() or, increment OSIntNesting directly;
Execute user code to service ISR;
Call OSIntExit();
Restore all CPU registers;
Execute a return from interrupt instruction;

Остальное происходит как описано в даташите на процессор, единственное нельзя ожидать событий от RTOS в прерываниях.
Go to the top of the page
 
+Quote Post
andrewlekar
сообщение Sep 19 2014, 10:56
Сообщение #7


Знающий
****

Группа: Участник
Сообщений: 837
Регистрация: 8-02-07
Пользователь №: 25 163



Штатные средства ОС такие, что обработчик прерывания вызывается через враппер, который делает всю работу по входу/выходу из прерывания. Если у вас вектор прерываний настроен на работу через этот враппер, то свой обработчик записываете в таблицу обработчиков ОС и он выполнится без дополнительных телодвижений.
Go to the top of the page
 
+Quote Post
billidean
сообщение Oct 11 2014, 14:08
Сообщение #8


Местный
***

Группа: Свой
Сообщений: 247
Регистрация: 4-10-10
Из: г. Екатеринбург
Пользователь №: 59 925



Код
void task2(void* pdata)
{
while (1)
{
alt_irq_register(BUTTONS_IRQ, (void*)BUTTONS_BASE, button_isr);
printf("Hello from task2\n");
//OSTimeDlyHMSM(0, 0, 1, 0);
}
}
Это вообще ... какая-то, в бесконечном цикле регить обработчик....

А вообще, более правильный механизм выглядит так:
1. регим обработчик прерывания
2. заводим семафор
3. заводим таск, которому нужно это прерывание
4. в обработчике прерывания взводим семафор
5. в таске, в начале тела ждем семафора, после чего делаем то, что надо, сбрасываем семафор
ну, это примерная модель, а уже для каждого конкретного случая может немного изменяться.
Go to the top of the page
 
+Quote Post

Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 19th April 2024 - 21:50
Рейтинг@Mail.ru


Страница сгенерированна за 0.01401 секунд с 7
ELECTRONIX ©2004-2016