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

 
 
> Два потока на си
sergey sva
сообщение Sep 10 2008, 12:53
Сообщение #1


Гуру
******

Группа: Свой
Сообщений: 2 546
Регистрация: 23-05-07
Из: Самарская область Сызрань
Пользователь №: 27 923



Как на си реализовать два потока, без использования ОС ? к примеру таймер 0 вызывает
программу обработки прерываний, в который происходит переключение между потоками.
Может что прочитать посоветуете или ссылку дадите.
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов
Rst7
сообщение Sep 14 2008, 13:51
Сообщение #2


Йа моск ;)
******

Группа: Модераторы
Сообщений: 4 345
Регистрация: 7-07-05
Из: Kharkiv-city
Пользователь №: 6 610



Цитата
Практически такие вещи на "чистом" С не напишешь


Как раз для камней типа AVR пишется на раз. Необходимые средства в штатной сишной библиотеке есть.

Код
#include <setjmp.h>

jmp_buf main_task;
jmp_buf rs_task;
char rs_rstack[8];
char rs_cstack[64];

__interrupt void CNTX_SWT(void)
{
  if (!setjmp(main_task)) //Запомнили контекст осн. задачи
  {
    longjmp(rs_task,1); //Перешли в контекст RS_TRX
  }
}


#pragma vector=USART0_RXC_vect
__interrupt __raw void rs_rx(void)
{
    ((void(*)(void))CNTX_SWT)();
}

#pragma vector=USART0_UDRE_vect
__interrupt __raw void rs_tx(void)
{
    ((void(*)(void))CNTX_SWT)();
}

#pragma vector=USART0_TXC_vect
__interrupt __raw void rs_txc(void)
{
    ((void(*)(void))CNTX_SWT)();
}

#pragma vector=TIMER1_OVF_vect
__interrupt __raw void rs_timeout(void)
{
    ((void(*)(void))CNTX_SWT)();
}

void wait_int()
{
  if (!setjmp(rs_task)) //Запомнили контекст RS_TASK
  {
    longjmp(main_task,1); //Перешли в контекст осн. задачи
  }
}

__task __noreturn RS_TRX(void)
{
  //Ну, например, вечное эхо
  for(;;)
  {
    char c;
    UCSR0B_RXCIE0=1; //Разрешили прерывания от приемника
    wait_int();
    c=UDR;
    UDR=c;
    UCSR0B_TXCIE0=1; //Разрешаем прерывания от передатчика
    wait_int(); //Ждемс
   }
}

void InitRS(void)
{
  __disable_interrupt();
  ((unsigned int *)rs_task)[10]=((unsigned int)rs_rstack)+7; //SP
  ((unsigned int *)rs_task)[8]=((unsigned int)rs_cstack)+64; //Y
  ((unsigned int *)rs_task)[9]=(unsigned int)RS_TRX; //Адрес перехода
  if (!setjmp(main_task)) longjmp(rs_task,1); //Переходим в RS_TRX
  __enable_interrupt();
}


Тут будет выполнен запуск фоновой задачи RS_TRX, которая будет ждать символа из уарта и отправлять его обратно, ждать готовности передатчика и по кругу.


--------------------
"Практика выше (теоретического) познания, ибо она имеет не только достоинство всеобщности, но и непосредственной действительности." - В.И. Ленин
Go to the top of the page
 
+Quote Post
Guest_Цыкетчик_*
сообщение Sep 24 2008, 13:25
Сообщение #3





Guests






Цитата(Rst7 @ Sep 14 2008, 17:51) *
Как раз для камней типа AVR пишется на раз. Необходимые средства в штатной сишной библиотеке есть.

ИМХО, это не от "камня" зависит а от разработчиков компилятора
Go to the top of the page
 
+Quote Post



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

 


RSS Текстовая версия Сейчас: 20th July 2025 - 17:49
Рейтинг@Mail.ru


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