blob: a3c7b201338debd2b47a21b81f4b0d4731676073 [file] [log] [blame]
/*******************************************************************************
* Copyright (C) Marvell International Ltd. and its affiliates
*
* Marvell GPL License Option
*
* If you received this File from Marvell, you may opt to use, redistribute and/or
* modify this File in accordance with the terms and conditions of the General
* Public License Version 2, June 1991 (the "GPL License"), a copy of which is
* available along with the File in the license.txt file or by writing to the Free
* Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 or
* on the worldwide web at http://www.gnu.org/licenses/gpl.txt.
*
* THE FILE IS DISTRIBUTED AS-IS, WITHOUT WARRANTY OF ANY KIND, AND THE IMPLIED
* WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE ARE EXPRESSLY
* DISCLAIMED. The GPL License provides additional details about this warranty
* disclaimer.
********************************************************************************/
#define _VPP_ISR_C_
#include "linux/sched.h" // for cpu_clock()
#include "thinvpp_module.h"
#include "thinvpp_apifuncs.h"
#include "thinvpp_isr.h"
#include "vpp.h"
#include "maddr.h"
#include "api_avio_dhub.h"
#include "avioDhub.h"
extern logo_device_t fastlogo_ctx;
extern int stop_flag;
extern int cpcb_start_flag;
extern unsigned last_isr_interval;
static int vbi_init=0;
#if LOGO_USE_SHM
static void set_bcm_cmd_0(THINVPP_OBJ *vpp_obj, unsigned bytes)
{
// first vpp commands are pre-loaded
BCMBUF *pbcmbuf = vpp_obj->pVbiBcmBuf;
pbcmbuf->writer += (bytes/sizeof(*pbcmbuf->writer));
}
#endif
static void set_bcm_cmd(THINVPP_OBJ *vpp_obj, unsigned * cmd, unsigned bytes)
{
BCMBUF *pbcmbuf = vpp_obj->pVbiBcmBuf;
memcpy(pbcmbuf->writer, cmd, bytes);
pbcmbuf->writer += (bytes/sizeof(*pbcmbuf->writer));
}
static void dma_logo_frame(THINVPP_OBJ *vpp_obj)
{
DHUB_CFGQ *src_cfgQ = vpp_obj->dv[CPCB_1].curr_cpcb_vbi_dma_cfgQ;
unsigned bytes = fastlogo_ctx.logo_dma_cmd_len;
#if LOGO_USE_SHM
// logo dma commands are pre-loaded
#else
memcpy(src_cfgQ->addr, fastlogo_ctx.logo_frame_dma_cmd, bytes);
#endif
src_cfgQ->len = bytes/8;
}
typedef struct _rect_win { unsigned left, top, right, bottom; } RECT_WIN;
typedef struct _RES_T { unsigned int HRes, VRes; } VPP_FE_DLR_INPUT_RES, *PVPP_FE_DLR_INPUT_RES;
/*the offset plus with input resolution to set dummy TG size*/
#define VPP_FE_DUMMY_TG_SIZE_H_OFF_P 20
#define VPP_FE_DUMMY_TG_SIZE_V_OFF_P 10
#define VPP_FE_DUMMY_TG_SIZE_H_OFF_I 22
#define VPP_FE_DUMMY_TG_SIZE_V_OFF_I 10
#define VPP_FE_DUMMY_TG_HS_FE 1
#define VPP_FE_DUMMY_TG_HS_BE 3
#define VPP_FE_DUMMY_TG_HB_FE_OFF 8
#define VPP_FE_DUMMY_TG_HB_BE 7
#define VPP_FE_DUMMY_TG_VB0_FE_OFF 3
#define VPP_FE_DUMMY_TG_VB0_BE 2
#define PIXEL_PER_BEAT_YUV_422 4
static const unsigned int VppFeDlrRegOff[] = {
RA_LDR_BG,
RA_LDR_MAIN,
RA_LDR_PIP,
RA_LDR_PG,
RA_LDR_IG,
RA_LDR_CURSOR,
RA_LDR_MOSD
};
typedef enum VPP_OVL_PLANE_UNIT_NUM_T
{
Vpp_OVL_PLANE0 = 0,
Vpp_OVL_PLANE1,
Vpp_OVL_PLANE2,
Vpp_OVL_PLANE3,
Vpp_OVL_PLANE3A,
Vpp_OVL_PLANE3B,
Vpp_OVL_PLANE3C,
Vpp_OVL_PLANE3D,
}VPP_OVL_PLANE_UNIT_NUM;
static unsigned CPCB1_VPP_OVL_PlaneColorRegOffset[] = {
CPCB0_OO_FIX0_0<<2,
CPCB0_OO_FIX1_0<<2,
CPCB0_OO_FIX2_0<<2,
CPCB0_OO_FIX3_0<<2,
CPCB0_OO_FIX3A_0<<2,
CPCB0_OO_FIX3B_0<<2,
CPCB0_OO_FIX3C_0<<2,
CPCB0_OO_FIX3D_0<<2,
};
static unsigned CPCB3_VPP_OVL_PlaneColorRegOffset[] = {
CPCB2_OO_FIX0_0<<2,
CPCB2_OO_FIX1_0<<2,
~0,
~0,
~0,
~0,
~0,
~0,
};
static unsigned CPCB1_VPP_OVL_BorderAlphaRegOffset[] = {
~0,
CPCB0_OO_P5_AL<<2,
CPCB0_OO_P6_AL<<2,
CPCB0_OO_P7_AL<<2,
CPCB0_OO_P7A_AL<<2,
CPCB0_OO_P7B_AL<<2,
CPCB0_OO_P7C_AL<<2,
CPCB0_OO_P7D_AL<<2,
};
static unsigned VPP_OVL_WeightRegOffset[] = {
CPCB0_VO_WEIGHT << 2,
CPCB1_VO_WEIGHT << 2,
~0,
~0
};
static unsigned* set_plane_widnow_helper(unsigned* Que, unsigned plane_addr, unsigned value)
{
*Que++ = value & 0xff;
*Que++ = plane_addr;
*Que++ = (value>>8) & 0xff;
*Que++ = plane_addr + 4;
return Que;
}
static unsigned* m_SetPlaneWindow(unsigned* Que, unsigned plane_addr, RECT_WIN *Win)
{
Que = set_plane_widnow_helper(Que, plane_addr + 0*8, Win->left);
Que = set_plane_widnow_helper(Que, plane_addr + 1*8, Win->right);
Que = set_plane_widnow_helper(Que, plane_addr + 2*8, Win->top);
Que = set_plane_widnow_helper(Que, plane_addr + 3*8, Win->bottom);
return Que;
}
static unsigned* m_THINVPP_CPCB_SetPlaneAttribute(unsigned* Que, THINVPP_OBJ *vpp_obj, int cpcbID, int layerID, int alpha, int bgcolor)
{
unsigned RegAddr;
// set plane background color
RegAddr = ~0;
if (cpcbID == CPCB_1)
{
RegAddr = CPCB1_VPP_OVL_PlaneColorRegOffset[layerID+1];
}
else if (cpcbID == CPCB_3)
{
RegAddr = CPCB3_VPP_OVL_PlaneColorRegOffset[layerID+1];
}
if (RegAddr == ~0)
return Que;
*Que++ = GET_LOWEST_BYTE(bgcolor);
*Que++ = (vpp_obj->base_addr + RegAddr);
*Que++ = GET_SECOND_BYTE(bgcolor);
*Que++ = (vpp_obj->base_addr + RegAddr + 4);
*Que++ = GET_THIRD_BYTE(bgcolor);
*Que++ = (vpp_obj->base_addr + RegAddr + 8);
// set plane source global alpha
if ((cpcbID > CPCB_1) || (layerID > CPCB1_PLANE_2))
return Que;
RegAddr = (CPCB0_OO_P1_AL << 2);
if (layerID == CPCB1_PLANE_2)
{
unsigned alpha2;
alpha2 = (vpp_obj->chan[CHAN_MAIN].zorder < vpp_obj->chan[CHAN_PIP].zorder)?
(alpha+1)/2: (256-alpha)/2;
//VPP_OVL_SetVideoBlendingFactor(vpp_obj, cpcbID, alpha2);
*Que++ = alpha2;
*Que++ = (vpp_obj->base_addr + VPP_OVL_WeightRegOffset[cpcbID]);
RegAddr += 4;
}
*Que++ = alpha;
*Que++ = (vpp_obj->base_addr + RegAddr);
// set plane border global alpha
RegAddr = CPCB1_VPP_OVL_BorderAlphaRegOffset[layerID+1];
*Que++ = alpha;
*Que++ = (vpp_obj->base_addr + RegAddr);
return Que;
}
static unsigned *m_THINVPP_CPCB_SetPlaneSourceWindow(unsigned *Que, THINVPP_OBJ *vpp_obj, int cpcbID, int layerID, int x, int y, int width, int height)
{
unsigned PlaneAddr;
RECT_WIN window;
window.left = x;
window.top = y;
window.right = x + width;
window.bottom = y + height;
switch (cpcbID){
case CPCB_1:
switch (layerID){
case CPCB1_PLANE_1: /* CPCB plane 1 */
PlaneAddr = vpp_obj->base_addr + (CPCB0_P1_SX_L << 2); // CPCB_1::TG_PLANE1_MAIN
Que = m_SetPlaneWindow(Que, PlaneAddr, &window);
PlaneAddr = vpp_obj->base_addr + (CPCB0_P1_CR1_SX_L << 2); // CPCB_1::TG_PLANE1_MAIN_CROP1
Que = m_SetPlaneWindow(Que, PlaneAddr, &window);
PlaneAddr = vpp_obj->base_addr + (CPCB0_P1_CR2_SX_L << 2); // CPCB_1::TG_PLANE1_MAIN_CROP1
Que = m_SetPlaneWindow(Que, PlaneAddr, &window);
break;
case CPCB1_PLANE_2: /* CPCB plane 2 */
PlaneAddr = vpp_obj->base_addr + (CPCB0_P2_SX_L << 2); // CPCB_1::TG_PLANE2_PIP
Que = m_SetPlaneWindow(Que, PlaneAddr, &window);
PlaneAddr = vpp_obj->base_addr + (CPCB0_P2_CR1_SX_L << 2); // CPCB_1::TG_PLANE2_PIP_CROP1
Que = m_SetPlaneWindow(Que, PlaneAddr, &window);
break;
}
break;
case CPCB_3:
switch (layerID){
case CPCB1_PLANE_1: /* CPCB plane 1 */
PlaneAddr = vpp_obj->base_addr + (CPCB2_P1_SX_L << 2); // CPCB_3::TG_PLANE1_MAIN
Que = m_SetPlaneWindow(Que, PlaneAddr, &window);
break;
}
break;
}
return Que;
}
static unsigned *m_FE_DLR_SetVPDMX(unsigned *Que, THINVPP_OBJ *vpp_obj, unsigned HRes, unsigned VRes)
{
*Que++ = (HRes-1);
*Que++ = (vpp_obj->base_addr + RA_Vpp_VP_DMX_HRES);
*Que++ = ((VRes/2)-1);
*Que++ = (vpp_obj->base_addr + RA_Vpp_VP_DMX_VRES);
*Que++ = (HRes + VPP_FE_DUMMY_TG_SIZE_H_OFF_I - 1);
*Que++ = (vpp_obj->base_addr + RA_Vpp_VP_DMX_HT);
*Que++ = (VRes + VPP_FE_DUMMY_TG_SIZE_V_OFF_I - 1);
*Que++ = (vpp_obj->base_addr + RA_Vpp_VP_DMX_IVT);
*Que++ = (VRes + VPP_FE_DUMMY_TG_SIZE_V_OFF_I - 1);
*Que++ = (vpp_obj->base_addr + RA_Vpp_VP_DMX_VT);
*Que++ = (1);
*Que++ = (vpp_obj->base_addr + RA_Vpp_VP_DMX_CTRL);
return Que;
}
static unsigned *m_FE_DLR_SetPlaneSize(unsigned *Que, THINVPP_OBJ *vpp_obj, int Channel, unsigned HRes, unsigned VRes, unsigned CropWpl)
{
unsigned int RegAddr = vpp_obj->base_addr + RA_Vpp_LDR + VppFeDlrRegOff[Channel];
/*write plane size to BCM buffer*/
*Que++ = (VRes + (HRes << 16));
*Que++ = (RegAddr + RA_PLANE_SIZE);
/*write crop WPL to BCM buffer*/
*Que++ = CropWpl;
*Que++ = (RegAddr + RA_PLANE_CROP);
return Que;
}
static unsigned *m_FE_DLR_SetDummyTG(unsigned *Que, THINVPP_OBJ *vpp_obj, unsigned HRes, unsigned VRes)
{
unsigned int RegAddr;
RegAddr = vpp_obj->base_addr + RA_Vpp_VP_TG;
/*write TG size*/
*Que++ = ((VRes + VPP_FE_DUMMY_TG_SIZE_V_OFF_P) + ((HRes + VPP_FE_DUMMY_TG_SIZE_H_OFF_P) << 16));
*Que++ = (RegAddr + RA_TG_SIZE);
/*write the H blank front edge value*/
*Que++ = (HRes + VPP_FE_DUMMY_TG_HB_FE_OFF + (VPP_FE_DUMMY_TG_HB_BE << 16));
*Que++ = (RegAddr + RA_TG_HB);
/*write the V blank front edge value*/
*Que++ = (VRes + VPP_FE_DUMMY_TG_VB0_FE_OFF + (VPP_FE_DUMMY_TG_VB0_BE << 16));
*Que++ = (RegAddr + RA_TG_VB0);
return Que;
}
static unsigned* m_UpdateVPSize(unsigned* Que, THINVPP_OBJ *vpp_obj, unsigned ihRes, unsigned ivRes)
{
unsigned int TotalInpPix, TotalOutPix;
unsigned int TotPixForWriteClient, TotPixForReadClient;
TotalInpPix =
TotalOutPix = ivRes * ihRes;
//THINVPP_BCMBUF_Write(vpp_obj->pVbiBcmBuf, vpp_obj->base_addr+RA_Vpp_vpIn_pix, TotalInpPix);
*Que++ = TotalInpPix;
*Que++ = (vpp_obj->base_addr+RA_Vpp_vpIn_pix);
//THINVPP_BCMBUF_Write(vpp_obj->pVbiBcmBuf, vpp_obj->base_addr+RA_Vpp_vpOut_pix, TotalOutPix);
*Que++ = TotalOutPix;
*Que++ = (vpp_obj->base_addr+RA_Vpp_vpOut_pix);
TotPixForWriteClient = (ivRes + 1) * ihRes;
TotPixForReadClient = (TotPixForWriteClient * 26 + 63) / 64;
//THINVPP_BCMBUF_Write(vpp_obj->pVbiBcmBuf, vpp_obj->base_addr+RA_Vpp_diW_pix, TotPixForWriteClient);
*Que++ = TotPixForWriteClient;
*Que++ = (vpp_obj->base_addr+RA_Vpp_diW_pix);
//THINVPP_BCMBUF_Write(vpp_obj->pVbiBcmBuf, vpp_obj->base_addr+RA_Vpp_diR_word, TotPixForReadClient);
*Que++ = TotPixForReadClient;
*Que++ = (vpp_obj->base_addr+RA_Vpp_diR_word);
return Que;
}
void init_vbi(THINVPP_OBJ *vpp_obj)
{
PLANE *plane = &vpp_obj->plane[PLANE_MAIN];
VBUF_INFO *pinfo = plane->pinfo;
unsigned *Que, *Cmd, *CmdEnd;
unsigned CropWpl;
#if LOGO_USE_SHM
Cmd = (unsigned *) fastlogo_ctx.bcmQ;
Que = (unsigned *) fastlogo_ctx.dmaQ;
#else
Cmd = (unsigned *) fastlogo_ctx.bcm_cmd_0;
Que = (unsigned *) logo_frame_dma_cmd;
#endif
CmdEnd = Cmd + (fastlogo_ctx.bcm_cmd_0_len/(sizeof(unsigned)));
//pinfo->m_active_left &= ~1;
//pinfo->m_active_width = ((pinfo->m_active_left + pinfo->m_active_width) & ~1) - pinfo->m_active_left;
CropWpl = (((pinfo->m_active_width + PIXEL_PER_BEAT_YUV_422 - 1) / PIXEL_PER_BEAT_YUV_422) << 16);
plane->wpl = (CropWpl>>16);
while (Cmd < CmdEnd)
{
switch (*Cmd & 0xf0000000)
{
case 0x80000000:
Cmd = m_THINVPP_CPCB_SetPlaneAttribute(Cmd, vpp_obj, 0, 0, pinfo->alpha, pinfo->bgcolor);
break;
case 0x90000000:
Cmd = m_FE_DLR_SetPlaneSize(Cmd, vpp_obj, 1, pinfo->m_active_width, pinfo->m_active_height, CropWpl);
break;
case 0xa0000000:
Cmd = m_FE_DLR_SetVPDMX(Cmd, vpp_obj, pinfo->m_active_width, pinfo->m_active_height);
break;
case 0xb0000000:
Cmd = m_FE_DLR_SetDummyTG(Cmd, vpp_obj, pinfo->m_active_width, pinfo->m_active_height);
break;
case 0xc0000000:
Cmd = m_UpdateVPSize(Cmd, vpp_obj, pinfo->m_active_width, pinfo->m_active_height);
break;
case 0xd0000000:
Cmd = m_THINVPP_CPCB_SetPlaneSourceWindow(Cmd, vpp_obj, 0, 0,
pinfo->m_active_left, pinfo->m_active_top, pinfo->m_active_width, pinfo->m_active_height);
break;
default:
Cmd += 2;
break;
}
}
START_2DDMA(plane->dmaRdhubID, plane->dmaRID,
(unsigned) pinfo->m_pbuf_start + (unsigned) pinfo->m_disp_offset, pinfo->m_buf_stride,
plane->wpl*8, plane->actv_win.height,
(unsigned int (*)[2])Que);
}
/////////////////////////////////////////////////////
// //
// Interrupt Service Routines for Berlin //
// //
/////////////////////////////////////////////////////
/********************************************************************************
* FUNCTION: start all active plane data loader of a VPP FE channel
* PARAMS: *vpp_obj - pointer to VPP object
* chanID - channel
* RETURN: MV_THINVPP_OK - succeed
* MV_THINVPP_EBADPARAM - invalid parameter
* MV_THINVPP_EUNCONFIG - plane not activated yet
*******************************************************************************/
static int startChannelDataLoader(THINVPP_OBJ *vpp_obj, int chanID)
{
int cpcbID;
CHAN *chan;
PLANE *plane;
cpcbID = CPCB_OF_CHAN(vpp_obj, chanID);
chan = &vpp_obj->chan[chanID];
if (chanID == CHAN_MAIN || chanID == CHAN_PIP) { /* none AUX channel */
int planeID = chanID;
plane = &vpp_obj->plane[planeID];
switch (plane->status) {
case STATUS_ACTIVE:
#if LOGO_USE_SHM
// first vpp commands are pre-loaded
set_bcm_cmd_0(vpp_obj, fastlogo_ctx.bcm_cmd_0_len);
#else
set_bcm_cmd(vpp_obj, fastlogo_ctx.bcm_cmd_0, fastlogo_ctx.bcm_cmd_0_len);
#endif
dma_logo_frame(vpp_obj);
plane->status = STATUS_DISP;
break;
case STATUS_DISP:
/* start data loader DMA to load display content */
dma_logo_frame(vpp_obj);
/* start read-back data loader */
set_bcm_cmd(vpp_obj, fastlogo_ctx.bcm_cmd_n, fastlogo_ctx.bcm_cmd_n_len);
break;
default:
break;
}
}
return (MV_THINVPP_OK);
}
static void toggleQ(THINVPP_OBJ *vpp_obj, int cpcbID)
{
THINVPP_BCMBUF_To_CFGQ(vpp_obj->pVbiBcmBuf, vpp_obj->dv[cpcbID].curr_cpcb_vbi_bcm_cfgQ);
THINVPP_BCMDHUB_CFGQ_Commit(vpp_obj->dv[cpcbID].curr_cpcb_vbi_bcm_cfgQ, cpcbID);
#if !LOGO_USE_SHM
// do no need double buffers for dhub queues
if (vpp_obj->pVbiBcmBufCpcb[cpcbID] == &vpp_obj->vbi_bcm_buf[0])
vpp_obj->pVbiBcmBufCpcb[cpcbID] = &vpp_obj->vbi_bcm_buf[1];
else
vpp_obj->pVbiBcmBufCpcb[cpcbID] = &vpp_obj->vbi_bcm_buf[0];
if (vpp_obj->dv[cpcbID].curr_cpcb_vbi_dma_cfgQ == &vpp_obj->dv[cpcbID].vbi_dma_cfgQ[0])
vpp_obj->dv[cpcbID].curr_cpcb_vbi_dma_cfgQ = &(vpp_obj->dv[cpcbID].vbi_dma_cfgQ[1]);
else
vpp_obj->dv[cpcbID].curr_cpcb_vbi_dma_cfgQ = &(vpp_obj->dv[cpcbID].vbi_dma_cfgQ[0]);
if (vpp_obj->dv[cpcbID].curr_cpcb_vbi_bcm_cfgQ == &vpp_obj->dv[cpcbID].vbi_bcm_cfgQ[0])
vpp_obj->dv[cpcbID].curr_cpcb_vbi_bcm_cfgQ = &(vpp_obj->dv[cpcbID].vbi_bcm_cfgQ[1]);
else
vpp_obj->dv[cpcbID].curr_cpcb_vbi_bcm_cfgQ = &(vpp_obj->dv[cpcbID].vbi_bcm_cfgQ[0]);
#endif
}
static void prepareQ(THINVPP_OBJ *vpp_obj, int cpcbID)
{
vpp_obj->dv[cpcbID].curr_cpcb_vbi_bcm_cfgQ->len = 0;
vpp_obj->dv[cpcbID].curr_cpcb_vbi_dma_cfgQ->len = 0;
vpp_obj->pVbiBcmBuf = vpp_obj->pVbiBcmBufCpcb[cpcbID];
THINVPP_BCMBUF_Select(vpp_obj->pVbiBcmBuf, cpcbID);
}
/* interrupt service routine for CPCB TG interrupt */
void THINVPP_CPCB_ISR_service(THINVPP_OBJ *vpp_obj, int cpcbID)
{
DV *pDV;
int params[2];
static int cpcb_isr_count=0;
cpcb_isr_count++;
if (!vpp_obj)
return;
if (cpcbID != CPCB_1)
return;
pDV = &(vpp_obj->dv[cpcbID]);
pDV->vbi_num ++; // VBI counter
switch (pDV->status) {
case STATUS_INACTIVE:
break;
case STATUS_ACTIVE:
/*when change cpcb output resolution, status was set to inactive, Dhub should be stopped at this moment*/
if (cpcbID != CPCB_1)
break;
/* stop fast-logo */
if(stop_flag == 1)
{
prepareQ(vpp_obj, cpcbID);
/* set resolution to RESET mode */
params[0] = CPCB_1;
params[1] = RES_RESET;
VPP_SetCPCBOutputResolution(vpp_obj, params);
set_bcm_cmd(vpp_obj, &fastlogo_ctx.bcm_cmd_z[0], fastlogo_ctx.bcm_cmd_z_len);
toggleQ(vpp_obj, cpcbID);
/* disable interrupt */
THINVPP_Enable_ISR_Interrupt(vpp_obj, CPCB_1, 0);
pDV->status = STATUS_INACTIVE;
stop_flag++;
break;
}
/* display fast-logo */
if (cpcb_start_flag == 3)
{
cpcb_start_flag = 4;
}
else
{
cpcb_start_flag++;
prepareQ(vpp_obj, cpcbID);
}
startChannelDataLoader(vpp_obj, CHAN_MAIN);
THINVPP_CFGQ_To_CFGQ(vpp_obj->dv[CPCB_1].curr_cpcb_vbi_dma_cfgQ, vpp_obj->dv[CPCB_1].curr_cpcb_vbi_bcm_cfgQ);
toggleQ(vpp_obj, cpcbID);
break;
case STATUS_STOP:
if (cpcbID != CPCB_1)
break;
prepareQ(vpp_obj, cpcbID);
params[0] = CPCB_1;
params[1] = RES_RESET;
VPP_SetCPCBOutputResolution(vpp_obj, params);
if(!(stop_flag > 0))
THINVPP_CFGQ_To_CFGQ(vpp_obj->dv[CPCB_1].curr_cpcb_vbi_dma_cfgQ, vpp_obj->dv[CPCB_1].curr_cpcb_vbi_bcm_cfgQ);
toggleQ(vpp_obj, cpcbID);
break;
default:
break;
}
}
/*************************************************************
* FUNCTION: register VPP interrupt service routine
* PARAMS: cpcbID - CPCB ID
* RETURN: none
*************************************************************/
void THINVPP_Enable_ISR_Interrupt(THINVPP_OBJ *vpp_obj, int cpcbID, int flag)
{
if (cpcbID == CPCB_1){
/* configure and enable CPCB0 interrupt */
semaphore_cfg(vpp_obj->pSemHandle, avioDhubSemMap_vpp_vppCPCB0_intr, 1, 0);
semaphore_pop(vpp_obj->pSemHandle, avioDhubSemMap_vpp_vppCPCB0_intr, 1);
semaphore_clr_full(vpp_obj->pSemHandle, avioDhubSemMap_vpp_vppCPCB0_intr);
if (flag)
{
if (!vbi_init)
{
init_vbi(vpp_obj);
}
vbi_init = 1;
flag = 1;
}
semaphore_intr_enable(vpp_obj->pSemHandle, avioDhubSemMap_vpp_vppCPCB0_intr, 0, flag, 0, 0, 0);
}
return;
}