/*****************************************************************************\

  File Name: pixel_compositor.c

  Description: This module contains pixel_compositor device specific functions.

  Copyright(c) 2007 Analog Devices Incorporated. All Rights Reserved.

  Revision History:


\*****************************************************************************/

/*****************************************************************************\

  Includes:

\*****************************************************************************/

#include <services/services.h>                /* system service includes */
#include <drivers/adi_dev.h>            
#include <SDK-ezkitutilities.h>
#include "adi_ssl_init.h"
#include "mediaplayer.h"
#include <drivers/pixc/adi_pixc.h>          	/* Pixel Compositor driver includes */
#include "adi_ssl_init.h"
#include "mediaplayer.h"	            
#include "devicecontrol.h"

/*****************************************************************************\

  Defines:

\*****************************************************************************/

/*****************************************************************************\

  Declarations:

\*****************************************************************************/

/* 2D buffers for Pixc */
section ("mpp_nocache")
ADI_DEV_2D_BUFFER InBufferPixc; 
section ("mpp_nocache")
ADI_DEV_2D_BUFFER OutBufferPixc;
/* handle to the PixC driver */
ADI_DEV_DEVICE_HANDLE PixcDriverHandle;

MPPMESSAGE	MsgToVideoTask;

/*****************************************************************************\

  Externs

\*****************************************************************************/

//section ("mpp_nocache") 
extern u8 	YUVBuf422		[800 * 608 *2 *4];  
extern OS_EVENT *video_decode_Q;
//section ("mpp_nocache")
extern u8 PingFrame[LCD_WIDTH * LCD_DATA_PER_PIXEL * LCD_HEIGHT];
extern ADI_DEV_DEVICE_HANDLE    LcdDriverHandle;
extern OS_EVENT *audio_decode_Q;


/*****************************************************************************\

  Function Prototypes

\*****************************************************************************/

void callback_pixel_compositor(void *AppHandle, u32 Event, void *pArg);
int init_pixel_compositor(void);
int close_pixel_compositor(void);
int enable_pixel_compositor(void);

/*****************************************************************************

    Function:       ConfigurePixc

    Description:    Opens and configures Pixel compositor for selected
                    color conversion mode.
                                        
*****************************************************************************/
int init_pixel_compositor(void)
{
    u32 Result = ADI_DEV_RESULT_SUCCESS;
    /* structure to hold Pixel compositor coversion mode */
    ADI_PIXC_CONVERSION_MODE    	PixcMode;
    u32 i;
        
        /* open the PixC driver */
        if((Result = adi_dev_Open(  adi_dev_ManagerHandle,          /* Dev manager Handle */
                                    &ADIPIXCEntryPoint,             /* Device Entry point */
                                    0,                              /* Device number    */
                                    NULL,                           /* No client handle */
                                    &PixcDriverHandle,              /* Device manager handle address */
                                    ADI_DEV_DIRECTION_BIDIRECTIONAL,/* Data Direction */
                                    adi_dma_ManagerHandle,          /* Handle to DMA Manager */
                                    NULL,                           /* Live callbacks */
                                    callback_pixel_compositor))     /* Callback Function */
                    != ADI_DEV_RESULT_SUCCESS) 
        {
            printf("Open PixC Failed!, Error Code: 0x%8X\n",Result);
        }

        /************** Configure Pixel Compositor ***************/

        /* Pixel compositor operating mode */
        PixcMode.InputFrame     = ADI_PIXC_FRAME_YUV422;		/* Input Frame Format 	*/
        PixcMode.OverlayAFrame  = ADI_PIXC_FRAME_DISABLE;		/* Overlay A Format 	*/
        PixcMode.OverlayBFrame  = ADI_PIXC_FRAME_DISABLE;		/* Overlay B Format 	*/
        PixcMode.OutputFrame    = ADI_PIXC_FRAME_RGB888;	/* Output Frame Format 	*/
    
        /* Pixel Compositor Configuration table */
        ADI_DEV_CMD_VALUE_PAIR PixcConfig[]=
        { 
            { ADI_DEV_CMD_SET_DATAFLOW_METHOD,              (void *)ADI_DEV_MODE_CHAINED		},  /* Dataflow method                      */
            { ADI_PIXC_CMD_SET_COLOR_CONVERSION_MODE,       (void *)&PixcMode               	},  /* Pixel compositor operating mode      */
            { ADI_PIXC_CMD_SET_PIXELS_PER_LINE,             (void *)LCD_WIDTH  	},  /* Pixels per line                      */
            { ADI_PIXC_CMD_SET_LINES_PER_FRAME,             (void *)LCD_HEIGHT	},  /* Lines per frame                      */
            { ADI_PIXC_CMD_ENABLE_ITUR656_SUPPORT,			(void *)TRUE                   	},  /* Enable ITU656 conversion                 */ 
            { ADI_PIXC_CMD_SET_TRANSPARENCY_COLOR_ENABLE,   (void *)FALSE                   	},  /* Disable Transparency                 */ 
            { ADI_DEV_CMD_END,                              NULL                            	}
        };

        /* Configure Pixel Compositor */
        if((Result = adi_dev_Control(PixcDriverHandle, ADI_DEV_CMD_TABLE, (void *) PixcConfig)) != ADI_DEV_RESULT_SUCCESS)
        {
            printf("Failed to configure PixC, Error Code: 0x%08X\n",Result);
        }

        /****************** Prepare PixC Input Image Buffer **********************/      
        /* No callback generated for Pixel Compositor Input image buffers */    
        InBufferPixc.Data                   = (void*)YUVBuf422;
        InBufferPixc.ElementWidth           = 4;
        InBufferPixc.XCount                 = (LCD_WIDTH*2/4);
        InBufferPixc.XModify                = 4;
        InBufferPixc.YCount                 = LCD_HEIGHT;
        InBufferPixc.YModify                = 4;
        InBufferPixc.CallbackParameter      = NULL;
        InBufferPixc.pNext                  = NULL;

      
        /****************** Prepare PixC Output Image Buffer **********************/
        /* PixC Output buffer */
        OutBufferPixc.Data                  = (void*)PingFrame;
        OutBufferPixc.ElementWidth          = 4;
        OutBufferPixc.XCount                = (LCD_WIDTH*3/4);
        OutBufferPixc.XModify               = 4;
        OutBufferPixc.YCount                = LCD_HEIGHT;
		OutBufferPixc.YModify           	= 4;
        OutBufferPixc.CallbackParameter     = &OutBufferPixc;
        OutBufferPixc.pNext                 = NULL;;
	
	/* enable pixel compositor */
	enable_pixel_compositor();

    
    /* return */
    return (Result);
}


/*********************************************************************

	Function:		callback_pixel_compositor

	Description:	callback for  the pixel compositor.  

*********************************************************************/
void callback_pixel_compositor(void *AppHandle, u32 Event, void *pArg)
{
    
    u32                 Result;

    /* CASEOF (event type) */
    switch (Event) 
    {    
        /* CASE (buffer processed) */
        case ADI_DEV_EVENT_BUFFER_PROCESSED:
    		MsgToVideoTask.uMID = MSGID_PIXEL_DONE;
			OSQPost(video_decode_Q, &MsgToVideoTask);

            break;
            
        default:
            printf("PixC Callback: Event not supported. Event code: 0x%08X \n",Event);
            break;
    }
    
    /* return */
}


/*********************************************************************

	Function:		close_pixel_compositor

	Description:	close the pixel compositor.  

*********************************************************************/
int close_pixel_compositor(void)
{
	u32 Result= ADI_DEV_RESULT_SUCCESS;
	
	if (Result == ADI_DEV_RESULT_SUCCESS)	
		Result = adi_dev_Control(PixcDriverHandle,ADI_DEV_CMD_SET_DATAFLOW, (void *) FALSE);   		
   		
   	if (Result == ADI_DEV_RESULT_SUCCESS)
   		Result = adi_dev_Close(PixcDriverHandle);
   		
   	return (Result);

}


/*********************************************************************

	Function:		enable_pixel_compositor

	Description:	enable the pixel compositor.  

*********************************************************************/
int enable_pixel_compositor(void)
{
	u32 Result= ADI_DEV_RESULT_SUCCESS;
   		
	/* Submit the PixC Input buffers*/
	if (Result == ADI_DEV_RESULT_SUCCESS)
    	Result = adi_dev_Write(PixcDriverHandle, ADI_DEV_2D, (ADI_DEV_BUFFER *) &InBufferPixc);

    /* submit the PixC Output buffer(s)*/
    if (Result == ADI_DEV_RESULT_SUCCESS)    
    	Result = adi_dev_Read(PixcDriverHandle, ADI_DEV_2D, (ADI_DEV_BUFFER *) &OutBufferPixc);
			
	/* Enable PixC dataflow */
	if (Result == ADI_DEV_RESULT_SUCCESS)	
		Result = adi_dev_Control(PixcDriverHandle,ADI_DEV_CMD_SET_DATAFLOW, (void *) TRUE);   		
   		   		
   	return (Result);

}

/*****/

