You can configure any type of video RTP endpoint to notify the application when an I-frame is detected, either received from IP and being sent to 324M, or received from 324M and being sent to IP.
For MPEG-4 and H.264 endpoints, if the I-frame reported was preceded by decoder configuration information (DCI), then this DCI is also reported in the returned event. An application can monitor DCI to determine changes in DCI. There may be cases where DCI changes require new signaling (for example, to close or reopen a new video logical channel for 324M upon a change in DCI).
Note: This feature is for full-duplex and simplex video endpoints. The procedure and example are shown for full-duplex endpoints.
To enable I-frame notification, create the MSP_CMD_RTPFDX_IFRAME_NOTIFY_CTRL command, and send it to the CG board.
The MSP_CMD_RTPFDX_IFRAME_NOTIFY_CTRL command uses the msp_ENDPOINT_RTPFDX_IFRAME_NOTIFY_CTRL structure to determine whether to enable or disable the I-frame notification functionality, and to determine when to generate the notifications.
For more information see Creating and sending MSPP commands and msp_ENDPOINT_RTPFDX_IFRAME_NOTIFY_CTRL.
The following events can be returned:
|
Event |
Description |
|
MSPEVN_SENDCOMMAND_DONE |
MSP_CMD_RTPFDX_IFRAME_NOTIFY_CTRL command was successfully sent to the specified endpoint on the CG board. |
|
MSPEVN_VIDEO_IFRAME_RTPIP |
An I-frame has come from the IP port. |
|
MSPEVN_VIDEO_IFRAME_H324 |
An I-frame has come from the PSTN port. |
If DCI is being reported with one of these I-frame events, the returned event buffer contains the following structure:
typedef struct
{
DWORD FilterId;
DWORD dciLen; //Length of DCI buffer
U8 dciData[MAX_DCI_BUF_SIZE]; //DCI data buffer (max 255 bytes)
} msp_RTP_VIDEO_DCI;
The following example shows how to enable I-frame notification in the 324M-to-IP direction for the H.264 full-duplex endpoint using the MSP handle ephd and to retrieve the returned DCI in the event buffer:
msp_ENDPOINT_RTPFDX_IFRAME_NOTIFY_CTRL notifyCmd;
notifyCmd.h324Notify = H2NMS_DWORD(1);
notifyCmd.ipNotify = H2NMS_DWORD(0);
command = mspBuildCommand(MSP_ENDPOINT_RTPFDX_VIDEO_H264,
MSP_CMD_RTPFDX_IFRAME_NOTIFY_CTRL);
ret = mspSendCommand(ephd, command, ¬ifyCmd, sizeof(notifyCmd));
expectedEvent = (MSPEVN_SENDCOMMAND_DONE |
MSP_CMD_RTPFDX_IFRAME_NOTIFY_CTRL);
if (WaitForSpecificEvent(gw, CtaQueueHd, expectedEvent, &event) != 0)
printf("\n\tERROR: mspSendCommand failed to send valid completion event\n");
. . .
//Process returned I-Frame unsolicited event
case MSPEVN_VIDEO_IFRAME_H324:
if(GwConfig[nGw].vidRtpEp[EP_OUTB].hd == pevent->objHd || GwConfig[nGw].vidRtpEp[EP_INB].hd == pevent->objHd)
{
printf("Unsol Event MSPEVN_VIDEO_IFRAME_H324 %s\n", event_val);
//Unsol events always return a buffer of at least 4 bytes for Filter ID field
if (pevent->buffer != NULL && pevent->size > 4)
{
U32 dciLength;
msp_RTP_VIDEO_DCI *pDCIEvent;
pDCIEvent = (msp_RTP_VIDEO_DCI*)(pevent->buffer);
dciLength = (U32)NMS2H_DWORD(pDCIEvent->dciLen);
if (dciLength > 0)
{
U8 *pDCIdata = pDCIEvent->dciData;
printf("DCI DATA (size = %d): \n", dciLength);
for (U32 i=0; i<dciLength; i++)
{
if(i%16 == 0)
printf("%02x: ",i);
printf(" %02x", pDCIdata[i]);
if (i%16 == 15)
printf("\n");
}
printf("\n");
}
}
}
break;