代码之家  ›  专栏  ›  技术社区  ›  Benoit

任务如何在多个vxworks队列上等待?

  •  3
  • Benoit  · 技术社区  · 16 年前

    我们有一个vxWorks设计,它需要一个任务来处理通过两个消息队列发送的高优先级和低优先级消息。
    必须按照FIFO顺序处理给定优先级的消息。

    例如,按接收顺序处理所有高优先级消息,然后处理低优先级消息。如果没有高优先级消息,则立即处理低优先级消息。

    2 回复  |  直到 16 年前
        1
  •  3
  •   JayG    16 年前


    每当触发select()时,您都会处理高优先级管道中的所有消息。然后处理来自低优先级管道的单个消息。然后再次调用select(循环)。

    示例代码段:

     // Initialization: Create high and low priority named pipes
     pipeDrv(); //initialize pipe driver
     int fdHi = pipeDevCreate("/pipe/high",numMsgs,msgSize);
     int fdLo = pipeDevCreate("/pipe/low",numMsgs,msgSize);
    
     ...
    
     // Message sending thread: Add messages to pipe
     write(fdHi, buf, sizeof(buf));
    
     ...
    
     // Message processing Thread: select loop
     fd_set rdFdSet;
    
     while(1)
     {
         FD_ZERO(&rdFdSet);
         FD_SET(fdHi, &rdFdSet);
         FD_SET(fdLo, &rdFdSet;
    
         if (select(FD_SETSIZE, &rdFdSet, NULL, NULL, NULL) != ERROR)
         {
             if (FD_ISSET(fdHi, &rdFdSet))
             {
                 // process all high-priority messages
                 while(read(fdHi,buf,size) > 0)
                 {
                     //process high-priority
                 }
             }
    
             if (FD_ISSET(fdLo, &rdFdSet))
             {
                 // process a single low priority message
                 if (read(fdLo,buf,size) > 0)
                 {
                     // process low priority
                 }
             }
         }
     }
    
        2
  •  1
  •   Benoit    16 年前

    在vxWorks中,您不能直接在多个队列上等待。但是,您可以使用OS事件(来自eventLib)来实现此结果。 下面是一个简单的代码片段:

    
    MSG_Q_ID lowQ, hiQ;
    
    void Init() {
    // Task Initialization Code.  This should be called from the task that will
    // be receiving the messages
    ...
    hiQ = msgQCreate(...);
    lowQ = msgQCreate(...);
    msgQEvStart(hiQ, VX_EV01);  // Event 1 sent when hiQ receives message
    msgQEvStart(loQ, VX_EV02);  // Event 2 sent when loQ receives message
    ...
    }
    void RxMessages() {
    ...
      UINT32 ev;   // Event received
    
       // Blocks until we receive Event 1 or 2
       eventReceive(VX_EV01 | VX_EV02, EVENT_WAIT_ANY, WAIT_FOREVER, &ev);
       if(ev & VX_EV01) {
          msgQReceive(hiQ, ...);
       }
       if(ev & VX_EV02) {
          msgQReceive(loQ, ...);
       }
    }
    

    请注意,您需要修改该代码,以确保在收到多条消息的情况下耗尽所有队列。

    同样的机制也可以使用semEvStart()函数应用于二进制信号量。