как запустить эту задачу таймера непрерывно?

0
static void timerHandler(int sig, siginfo_t *si, void *uc)
{
  timer_t *tidp;

  tidp = si->si_value.sival_ptr;

  if (*tidp == firstTimerID)

    TASK1(Task2ms_Raster);
  else if (*tidp == secondTimerID)
    TASK2(Task10ms_Raster);
  else if (*tidp == thirdTimerID)
    TASK3(Task100ms_Raster);
}

static int makeTimer(char *name, timer_t *timerID, int expireMS, int intervalMS)
{
  //sigset_t mask;
  struct sigevent te;
  struct itimerspec its;
  struct sigaction sa;
  int sigNo = SIGRTMIN;

  /* Set up signal handler. */
  memset(&sa, 0, sizeof(sa));
  sa.sa_flags = SA_SIGINFO;
  sa.sa_sigaction = timerHandler;
  sigemptyset(&sa.sa_mask);
  if (sigaction(sigNo, &sa, NULL) == -1)
  {
    perror("sigaction");
  }

  /* Set and enable alarm */
  te.sigev_notify = SIGEV_SIGNAL;
  te.sigev_signo = sigNo;
  te.sigev_value.sival_ptr = timerID;
  timer_create(CLOCK_REALTIME, &te, timerID);

  its.it_interval.tv_sec = 0;
  its.it_interval.tv_nsec = intervalMS * 1000000;
  its.it_value.tv_sec = 0;
  its.it_value.tv_nsec = expireMS * 1000000;
  timer_settime(*timerID, 0, &its, NULL);

  return 1;

}

int CreateSocket()
{

  socklen_t len = sizeof(client);
  // Socket creation for UDP

  acceptSocket = socket(AF_INET, SOCK_DGRAM, 0);

  if (acceptSocket == -1)

  {
    printf("Failure: socket creation is failed, failure code\n");

    return 1;
  }
  else
  {
    printf("Socket started!\n");

  }

  //non blocking mode
  /* rc = ioctl(acceptSocket, FIONBIO, (char *)&flag);
   if (rc < 0)
   {
   printf("\n ioctl() failed \n");
   return 0;
   }*/

  //Bind the socket
  memset(&addr, 0, sizeof(addr));

  addr.sin_family = AF_INET;

  addr.sin_port = htons(port);

  addr.sin_addr.s_addr = htonl(INADDR_ANY);

  rc = bind(acceptSocket, (struct sockaddr*) &addr, sizeof(addr));

  if (rc == -1)
  {
    printf("Failure: listen, failure code:\n");

    return 1;
  }
  else
  {
    printf("Socket an port %d \n", port);

  }

  if (acceptSocket == -1)
  {
    printf("Fehler: accept, fehler code:\n");

    return 1;
  }
  else
  {
    while (rc != -1)
    {

      rc = recvfrom(acceptSocket, buf, 256, 0, (struct sockaddr*) &client,
          &len);
      if (rc == 0)
      {
        printf("Server has no connection..\n");
        break;
      }
      if (rc == -1)
      {
        printf("something went wrong with data %s", strerror(errno));
        break;
      }

      XcpIp_RxCallback((uint16) rc, (uint8*) buf, (uint16) port);
      makeTimer("First Timer", &firstTimerID, 2, 2);   //2ms
      makeTimer("Second Timer", &secondTimerID, 10, 10);    //10ms
      makeTimer("Third Timer", &thirdTimerID, 100, 100);  //100ms
      while (1)
        ;;

    }
  }

  close(acceptSocket);

  return 0;

}

int main()
{
  Xcp_Initialize();
  CreateSocket();
  return 2;
}

void XcpApp_IpTransmit(uint16 XcpPort, Xcp_StatePtr8 pBytes, uint16 numBytes)
{
  if ((long) XcpPort == port)
  {
    sentbytes = sendto(acceptSocket, (char*) pBytes, (long) numBytes, 0,
        (struct sockaddr*) &client, sizeof(client));
  }
  XcpIp_TxCallback(port, (uint16) sentbytes);
}

Я работаю над клиентской и серверной архитектурой. Код сервера показан выше, и я создал сокет, чтобы получить запрос от клиента через IP-адрес и номер порта. Сервер ожидает запроса от клиента и отправляет ответ клиенту. когда он получает данные от клиента, он должен вызывать задачу таймера (т.е. callBackTimers в моем коде), для этого я также создал таймер для вызова задачи на каждые 2 мс, 10 мс и 100 мс.

Мой вопрос: в режиме отладки - контроль достигает вызова функции maketimer, но он не запускается автоматически (я не добавил точку останова). он останавливается при maketimer3. Как заставить его работать без остановки?

  • 0
    Вы могли бы показать код для makeTimer() ?
  • 0
    Теперь я добавил код таймера.
Показать ещё 5 комментариев
Теги:
handler
timer

2 ответа

1

Как я уже сказал в предыдущем вопросе, это, вероятно, связано с вашей функцией CreateSocket, а именно:

while(rc!=-1)
{
     rc=recvfrom(acceptSocket,buf, 256, 0, (struct sockaddr*) &client, &len);
     if(rc==0)
     {
       printf("Server has no connection..\n");
       break;
     }
     if(rc==-1)
     {
         printf("something went wrong with data %s", strerror(errno));
       break;
     }

     XcpIp_RxCallback( (uint16) rc, (uint8*) buf, (uint16) port );

     makeTimer("First Timer", &firstTimerID, 2, 2);   //2ms
     makeTimer("Second Timer", &secondTimerID, 10, 10);    //10ms
     makeTimer("Third Timer", &thirdTimerID, 100, 100);  //100ms

     while(1)
     ;;
}

Вы каждый раз создаете новые таймеры через этот цикл. Вы никогда не удаляете их. Существует ограничение на количество таймеров, которые вы можете создать. От man (2) timer_create:

Ядро предварительно распределяет "сигнал в реальном времени в реальном времени" для каждого таймера, созданного с помощью функции timer_create(). Следовательно, количество таймеров ограничено пределом ресурса RLIMIT_SIGPENDING (см. Setrlimit (2)).

Вы не проверяете статус кода возврата timer_create и я предполагаю, что у вас закончились таймеры, а после этого они просто терпят неудачу.

(Кстати, не уверен, что такое while(1);; должен это делать. Я понимаю разочарование, которое вы должны чувствовать, но это становится чем-то вроде движущейся цели.)

  • 0
    большое Вам спасибо . Можно ли запустить этот таймер независимо или параллельно с данными, полученными из сокета?
0

Вот поспешно (но я думаю, точнее) нарезал версию вашего кода. Из-за вашего while(1); в CreateSocket он просто собирается создать 3 таймера. Если вы запустите его, вы увидите, что запущены TASKS1/2/3. Это само по себе не является вашей проблемой.

#define _POSIX_C_SOURCE 199309
#include <stdio.h>
#include <signal.h>
#include <unistd.h>
#include <stdlib.h>
#include <time.h>
#include <string.h>


timer_t firstTimerID, secondTimerID, thirdTimerID;

void TASK1() {printf("task 1\n");}
void TASK2() {printf("task 2\n");}
void TASK3() {printf("task 3\n");}


static void timerHandler(int sig, siginfo_t *si, void *uc)
{
  timer_t *tidp;

  tidp = si->si_value.sival_ptr;

  if (*tidp == firstTimerID)
    TASK1();
  else if (*tidp == secondTimerID)
    TASK2();
  else if (*tidp == thirdTimerID)
    TASK3();
}

static int makeTimer(char *name, timer_t *timerID, int expireMS, int intervalMS)
{
  //sigset_t mask;
  struct sigevent te;
  struct itimerspec its;
  struct sigaction sa;
  int sigNo = SIGRTMIN;

  /* Set up signal handler. */
  memset(&sa, 0, sizeof(sa));
  sa.sa_flags = SA_SIGINFO;
  sa.sa_sigaction = timerHandler;
  sigemptyset(&sa.sa_mask);
  if (sigaction(sigNo, &sa, NULL) == -1)
  {
    perror("sigaction");
  }

  /* Set and enable alarm */
  te.sigev_notify = SIGEV_SIGNAL;
  te.sigev_signo = sigNo;
  te.sigev_value.sival_ptr = timerID;
  timer_create(CLOCK_REALTIME, &te, timerID);

  its.it_interval.tv_sec = 0;
  its.it_interval.tv_nsec = intervalMS * 1000000;
  its.it_value.tv_sec = 0;
  its.it_value.tv_nsec = expireMS * 1000000;
  timer_settime(*timerID, 0, &its, NULL);

  return 1;

}

int CreateSocket()
{
    int rc = 5;

    while (rc != -1)
    {
      makeTimer("First Timer", &firstTimerID, 2, 2);   //2ms
      makeTimer("Second Timer", &secondTimerID, 10, 10);    //10ms
      makeTimer("Third Timer", &thirdTimerID, 100, 100);  //100ms

      while (1);;
    }

  return 0;
}

int main()
{
  CreateSocket();
  return 2;
}

Позаботьтесь о проблеме с петлей и посмотрите, куда вы должны идти оттуда. Создайте 3 таймера. Если вы хотите, чтобы они уходили только один раз на один сокет, то либо не имеют значения интервала, чтобы они не повторяли или не выключали таймеры (т.е. нулевое значение значения/интервала) после первого раза, когда они уходят, Но в любом случае вы должны их повторно использовать.

  • 0
    большое Вам спасибо . Можно ли запустить этот таймер независимо или параллельно с данными, полученными из сокета?
  • 0
    Да, но вам нужно указать, что вы действительно хотите сделать. Независимые и параллельные являются взаимоисключающими в этом контексте. Вы хотите, чтобы при чтении через сокет таймеры устанавливались или просто отключались независимо от чтения?
Показать ещё 2 комментария

Ещё вопросы

Сообщество Overcoder
Наверх
Меню