SCOM

  • SCOM:Synchronized COMmunication module

  • 使用的时候要包含:#include <scom.h>

  • 使用的类型和常数
    typedef struct SCOM_Attrs {     /* SCOM object creation attributes */
    Char dummy;                     /* no attributes at present */
    } SCOM_Attrs;
    typedef struct SCOM_Obj SCOM_Obj, *SCOM_Handle;     /* SCOM object handle */
    extern SCOM_Attrs SCOM_ATTRS;                       /* default SCOM creation attributes */

  • 描述:这个模块在任务之间传送消息。它允许用户创建任意个异步的队列,并把消息发到这些队列中而且可以
    从这些队列中读取消息。这些消息是任意大小的缓存区。

  • SCOM模块管理SCOM队列对象。每一个SCOM队列内部使用一个队列对象(QUE)和一个旗语对象(SEM)。在SCOM队列的
    结构在SCOM模块中是私有的。应用程序不应该涉及到SCOM队列的对象。

  • 一个队列可以拥有任意个消息,但是消息的第一个域必须是QUE_elem。如:
    typedef struct ScomBufChannels {
        QUE_Elem elem;
        Sample *bufChannel[ NUMCHANNELS ];
    } ScomBufChannels;

    Let us look at a general case where some tasks A and B want to exchange messages. Tasks A
    and B agree that A sends data of type MyMsg to B via SCOM queues named "scomA" for task
    A, and "scomB" for task B. The following steps would occur:

  • SCOM 用到的函数:

    • SCOM_init().    Initializes the module.
    • SCOM_exit().    Ends use of the module.
    • SCOM_create().  Creates a new SCOM queue object.
    • SCOM_open().    Gets a reference to an existing SCOM queue object by name.
    • SCOM_delete().  Deallocates and deletes an SCOM queue object.
    • SCOM_putMsg().  Places SCOM message in an SCOM queue.
    • SCOM_getMsg().  Receives SCOM message from an SCOM queue.

    分析:
    SCOM_create()得到SCOM队列的句柄。
    Syntax scomQueue = SCOM_create(queueName, *attrs);
    Parameters     String queueName; /* Name of SCOM queue to create */
    SCOM_Attrs     *attrs; /* SCOM object attributes; only NULL supported */
    Return Value  SCOM_Handle /* handle of new SCOM queue */

    上面的表描述了两个任务之间的通信。一旦一个线程建立了一个队列,那么我们就可以在另一个线程里通过SCOM_open()来通信。


  • 例子:

    定义:
    SCOM_Handle objSCOMINToDIS[NUM_SCOM_OBJS_IN][2];

    Ptr msgSCOMInToProc[NUM_SCOM_OBJS_IN];
    在main()函数中
     /*-------------------------------------------------------*/
    /* create all SCOM and message objects */
    /*-------------------------------------------------------*/
    objSCOMINToDIS[0][0] = SCOM_create("IN1TODIS", NULL);
    objSCOMINToDIS[0][1] = SCOM_create("DISTOIN1", NULL);

    objSCOMINToDIS[1][0] = SCOM_create("IN2ATODIS", NULL);
    objSCOMINToDIS[1][1] = SCOM_create("DISTOIN2A", NULL);

    objSCOMINToDIS[2][0] = SCOM_create("IN2BTODIS", NULL);
    objSCOMINToDIS[2][1] = SCOM_create("DISTOIN2B", NULL);
    在采集线程1中:
    FVID_Frame *capFrameBuf;
    SCOM_Handle fromInput1toDIS,fromDIStoInput1;

    /*打开SCOM模块*/
    fromInput1toDIS = SCOM_open("IN1TODIS");
    fromDIStoInput1 = SCOM_open("DISTOIN1");
    /*申请一个空间*/
    FVID_alloc(capChanCh1, &capFrameBuf);

    while(1)
    {
    /*-----------------------------------------------------------*/
    /* Send message to process task with pointers to captured frame*/
    /*-----------------------------------------------------------*/
    SCOM_putMsg(fromInput1toDIS, (FVID_Frame *)capFrameBuf);

    /*-----------------------------------------------------------*/
    /* Wait for the message from the process task */
    /*-----------------------------------------------------------*/
    SCOM_getMsg(fromDIStoInput1, SYS_FOREVER);

    /*-----------------------------------------------------------*/
    /* Capture a new frame. */
    /*-----------------------------------------------------------*/
    FVID_exchange(capChanCh1, &capFrameBuf);
    }
    采集线程2中:
    FVID_Frame *capFrameBuf;
    SCOM_Handle fromInput2atoDIS,fromDIStoInput2a;

    /*打开SCOM模块*/
    fromInput2atoDIS = SCOM_open("IN2ATODIS");
    fromDIStoInput2a = SCOM_open("DISTOIN2A");
    /*申请一个空间*/
    FVID_alloc(capChanCh2a, &capFrameBuf);

    while(1)
    {
    /*-----------------------------------------------------------*/
    /* Send message to process task with pointers to captured frame*/
    /*-----------------------------------------------------------*/
    SCOM_putMsg(fromInput2atoDIS, (FVID_Frame *)capFrameBuf);

    /*-----------------------------------------------------------*/
    /* Wait for the message from the process task */
    /*-----------------------------------------------------------*/
    SCOM_getMsg(fromDIStoInput2a, SYS_FOREVER);

    /*-----------------------------------------------------------*/
    /* Capture a new frame. */
    /*-----------------------------------------------------------*/
    FVID_exchange(capChanCh2a, &capFrameBuf);
    }
    显示线程3中:
    void tskVideoLoopback()
    {
    Int i;

    SCOM_Handle fromInput1toDIS,fromDIStoInput1;
    SCOM_Handle fromInput2atoDIS,fromDIStoInput2a;
    SCOM_Handle fromInput2btoDIS,fromDIStoInput2b;

    FVID_Frame *capFrameBuf;
    FVID_Frame *disFrameBuf;
    /*设置显示的行数*/
    Int numLinesDis = EVMDM642_vDisParamsChan.imgVSizeFld1;
    /*设置采集的行数*/
    Int numLinesCap = SEEDVPM642_vCapParamsChan.fldYStop1 -
    SEEDVPM642_vCapParamsChan.fldYStrt1+1;
    /*判断是显示区域大,还是采集区域大,取其小者*/
    Int numLines = (numLinesDis > numLinesCap) ? numLinesCap : numLinesDis;
    /*设置采集像素数*/
    Int numPixels = (SEEDVPM642_vCapParamsChan.fldXStop1 -
    SEEDVPM642_vCapParamsChan.fldXStrt1+1)/2;
    /*设置采集行的增量*/
    Int capLinePitch = (SEEDVPM642_vCapParamsChan.fldXStop1 -
    SEEDVPM642_vCapParamsChan.fldXStrt1+1)/2;
    /*设置显示行的增量*/
    Int disLinePitch = EVMDM642_vDisParamsChan.imgHSizeFld1;

    // numLines *= 2; /* both fields */

    /*打开SCOM模块*/
    fromInput1toDIS = SCOM_open("IN1TODIS");
    fromDIStoInput1 = SCOM_open("DISTOIN1");

    fromInput2atoDIS = SCOM_open("IN2ATODIS");
    fromDIStoInput2a = SCOM_open("DISTOIN2A");

    fromInput2btoDIS = SCOM_open("IN2BTODIS");
    fromDIStoInput2b = SCOM_open("DISTOIN2B");
    /*申请一个空间*/
    FVID_alloc(disChan, &disFrameBuf);

    while(1)
    {
    /*-----------------------------------------------------------*/
    /* Wait for the message from the process task to recieve new */
    /* frame to be displayed. */
    /*-----------------------------------------------------------*/
    capFrameBuf = (FVID_Frame *)SCOM_getMsg(fromInput1toDIS, SYS_FOREVER);

    /*将数据放入相应的显示缓冲区*/
    for(i = 0; i < numLines; i ++)
    {
    DAT_copy(capFrameBuf->frame.iFrm.y1 + i * capLinePitch,
    disFrameBuf->frame.iFrm.y1 + i * disLinePitch+352,
    numPixels);
    DAT_copy(capFrameBuf->frame.iFrm.cb1 + i * (capLinePitch >> 1),
    disFrameBuf->frame.iFrm.cb1 + i * (disLinePitch >> 1)+172,
    numPixels>>1);

    DAT_copy(capFrameBuf->frame.iFrm.cr1 + i * (capLinePitch >> 1),
    disFrameBuf->frame.iFrm.cr1 + i * (disLinePitch >> 1)+172,
    numPixels>>1);
    }
    // DAT_wait(DAT_XFRID_WAITALL);
    /*-----------------------------------------------------------*/
    /* Wait for the message from the process task to recieve new */
    /* frame to be displayed. */
    /*-----------------------------------------------------------*/
    capFrameBuf = (FVID_Frame *)SCOM_getMsg(fromInput2atoDIS, SYS_FOREVER);
    /*将数据放入相应的显示缓冲区*/
    for(i = 0; i < numLines; i ++)
    {
    DAT_copy(capFrameBuf->frame.iFrm.y1 + i * capLinePitch,
    disFrameBuf->frame.iFrm.y1 + i * disLinePitch+720*287,
    numPixels);
    DAT_copy(capFrameBuf->frame.iFrm.cb1 + i * (capLinePitch >> 1),
    disFrameBuf->frame.iFrm.cb1 + i * (disLinePitch >> 1)+360*287,
    numPixels>>1);

    DAT_copy(capFrameBuf->frame.iFrm.cr1 + i * (capLinePitch >> 1),
    disFrameBuf->frame.iFrm.cr1 + i * (disLinePitch >> 1)+360*287,
    numPixels>>1);
    }
    // DAT_wait(DAT_XFRID_WAITALL);
    /*-----------------------------------------------------------*/
    /* Wait for the message from the process task to recieve new */
    /* frame to be displayed. */
    /*-----------------------------------------------------------*/
    capFrameBuf = (FVID_Frame *)SCOM_getMsg(fromInput2btoDIS, SYS_FOREVER);
    /*将数据放入相应的显示缓冲区*/
    for(i = 0; i < numLines; i ++)
    {
    DAT_copy(capFrameBuf->frame.iFrm.y1 + i * capLinePitch,
    disFrameBuf->frame.iFrm.y1 + i * disLinePitch+720*287+352,
    numPixels);
    DAT_copy(capFrameBuf->frame.iFrm.cb1 + i * (capLinePitch >> 1),
    disFrameBuf->frame.iFrm.cb1 + i * (disLinePitch >> 1)+360*287+172,
    numPixels>>1);

    DAT_copy(capFrameBuf->frame.iFrm.cr1 + i * (capLinePitch >> 1),
    disFrameBuf->frame.iFrm.cr1 + i * (disLinePitch >> 1)+360*287+172,
    numPixels>>1);
    }

    DAT_wait(DAT_XFRID_WAITALL);
    CACHE_clean(CACHE_L2ALL,NULL,NULL);
    /*-----------------------------------------------------------*/
    /* Display the decoded frame. */
    /*-----------------------------------------------------------*/
    FVID_exchange(disChan, &disFrameBuf);

    /*-----------------------------------------------------------*/
    /* Send message to process task to continue */
    /*-----------------------------------------------------------*/
    SCOM_putMsg(fromDIStoInput1, NULL);/* loop forever */
    /*-----------------------------------------------------------*/
    /* Send message to process task to continue */
    /*-----------------------------------------------------------*/
    SCOM_putMsg(fromDIStoInput2a, NULL);/* loop forever */
    /*-----------------------------------------------------------*/
    /* Send message to process task to continue */
    /*-----------------------------------------------------------*/
    SCOM_putMsg(fromDIStoInput2b, NULL);/* loop forever */
    }
    }

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值