/*****************************************************************************\

  File Name: mgr_application.c

  Description: 

  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"

/*****************************************************************************\

  Defines:

\*****************************************************************************/

/*****************************************************************************\

  Declarations:

\*****************************************************************************/
/* queue to hold message from INPUT-devices  */
OS_EVENT *mgr_application_Q;	
/* Empty void* array to hold Q messages */
void* mgr_application_arr[SZ_MSGQ_APP_INPUTDEV];

/* queue to hold APP to PLAYER commands */
OS_EVENT *mgr_player_Q;	
/* Empty void* array to hold Q messages */
void* mgr_player_arr[SZ_MSGQ_APP_CMD]; 

/* queue to hold APP to FILEMGR commands */
OS_EVENT *mgr_filesystem_Q;	
/* Empty void* array to hold Q messages */
void* mgr_filesystem_arr[SZ_MSGQ_APP_CMD]; 
 
OS_EVENT *mgr_display_Q;
void* mgr_display_arr[SZ_MSGQ_APP_CMD];

OS_EVENT *mediaplayer_Q;
void* mediaplayer_arr[SZ_MSGQ_APP_CMD];

semaphore_t mpEvents[] = 
{     
    {(void *)0,(void *)0},/* application event */
    {(void *)0,(void *)0},/* player event */   
    {(void *)0,(void *)0},/* filesystem event */        
    {(void *)0,(void *)0},/* display event */
    {(void *)0,(void *)0} /* mediaplayer event */
};

section("sdram0_bank2_stack") static OS_STK stack[THRD_STACKSIZE * sizeof(OS_STK)];

/*****************************************************************************\

  Externs:

\*****************************************************************************/


/*****************************************************************************\

  Function Prototypes:

\*****************************************************************************/

void init_mgr_application(void);
void launch_mgr_application(void) ;
void thread_mgr_application(void *pEvent);

static void close_devicecontrol(void);
static void SetMPPState(u32 cmd);


/*********************************************************************

	Function:	init_mgr_application																			
	
 	Parameters:	None 
																		
 	Return:		None														
																			
 	Description:	Initializes the application manager.
 	
*********************************************************************/
//section ("sdram0_bank3_app")
void init_mgr_application(void)
{
	/* set default STATE_IDLE */
	SetMPPState(MSGID_PLAYER_STOP);

    /* launch a task to receive messages the media player application*/	
    launch_mgr_application();	
}
			

/*********************************************************************

	Function:	launch_mgr_application																			
	
 	Parameters:	None 
																		
 	Return:		None														
																			
 	Description:	Launches a task thread which handles all input devices.
*********************************************************************/
section ("sdram0_bank2_thread")
void launch_mgr_application(void) 
{
	/*OS_STK *stack;*/
	int Result;
	INT32U i;
	
	
	/* Create app-inputdevices message Queue */
	mgr_application_Q = OSQCreate(mgr_application_arr, SZ_MSGQ_APP_INPUTDEV);
	mpEvents[0].sem = mgr_application_Q;
	
	
	Result = OSTaskCreateExt(thread_mgr_application, 
						(void *)&mpEvents[0], 
						&stack[THRD_STACKSIZE -1], 
						THRD_PRIORITY_MANAGER_APPLICATION, 
						MANAGER_APPLICATION_ID, 
						&stack[0], 
						THRD_STACKSIZE , 
						(void *)0, 
						OS_TASK_OPT_STK_CHK );
	if(Result && APP_TRACE_LEVEL)
	{
		APP_TRACE("OSTaskCreateExt:thread_mgr_application failed %d\n",Result);
		ezErrorCheck(1);

	}
	
	/* create a pause-button semaphore for the decoder */
	adi_sem_Create( 0, &PauseSemaphoreHandle, NULL );
					
}// end of launch_threads


/*********************************************************************

	Function:	thread_mgr_application																			
	
 	Parameters:	None 
																		
 	Return:		None														
																			
 	Description:	Monitors events from keypad, thumbwheel 
 					Directs messages to managers or devices
*********************************************************************/
section ("sdram0_bank2_thread")
void thread_mgr_application(void *pEvent)
{
	INT8U err;

	MPPMESSAGE	*pMessage;
	MPPMESSAGE	MessageToPlayer;
	MPPMESSAGE	MessageToFileManager;
	MPPMESSAGE	MessageToDisplay;

	semaphore_t *p;

	p = (semaphore_t *)pEvent;
	
	OS_EVENT *queue = p->sem;


    while(1)
	{
		
	    // pend on message queue
	    pMessage = (MPPMESSAGE *) OSQPend (queue, 0, &err);
		if (err && APP_TRACE_LEVEL) 
		{ 
			APP_TRACE("thread_mgr_application OSQPend error %d\n",err);
		}

		switch(pMessage->uMID)
		{
				/* message to select previous file */
				case MSGID_PREV_ENTRY:
					MessageToFileManager.uMID = MSGID_PREV_ENTRY;
					err = OSQPost(mgr_filesystem_Q, &MessageToFileManager);
					break;
					
				/* message to select the next file */	
				case MSGID_NEXT_ENTRY:
					MessageToFileManager.uMID = MSGID_NEXT_ENTRY;
					err= OSQPost(mgr_filesystem_Q, &MessageToFileManager);
					break;				
				
				/* message to Select,Play or Pause (they are share the same key) */	
				case MSGID_PLAYER_PLAY:	
					if (MPPState == STATE_IDLE)
					{
						/*send SELECT msg to FileMgr */
						MessageToFileManager.uMID = MSGID_FILE_SELECT;
						err = OSQPost(mgr_filesystem_Q, &MessageToFileManager);
					}
					else if (MPPState == STATE_PLAY)
					{
						/* set PAUSE flag */
						PauseButton = TRUE;
						/* send PAUSE msg to Player */
						MessageToPlayer.uMID = MSGID_PLAYER_PAUSE;
						err = OSQPost(mgr_player_Q, &MessageToPlayer);
					
						/* set the state status */
						SetMPPState(MSGID_PLAYER_PAUSE);
					}
					else /* STATE_PAUSE */
					{
						/* set RESUME flag */
						adi_sem_Post(PauseSemaphoreHandle);/* unlock the decoder */
						PauseButton = FALSE;
						/* send RESUME msg to Player */
						MessageToPlayer.uMID = MSGID_PLAYER_RESUME;
						err = OSQPost(mgr_player_Q, &MessageToPlayer);
										
						/* set the state status */
						SetMPPState(MSGID_PLAYER_RESUME);
					}
					break;
									
				/* message to Stop the player */
				case MSGID_PLAYER_STOP:
			 
				 	StopButton = TRUE;
					
					if(MPPState == STATE_PAUSE)
					{
						adi_sem_Post(PauseSemaphoreHandle);/* unlock the decoder */
						PauseButton = FALSE;
					}
					
					if ((MPPState == STATE_PLAY) || (MPPState == STATE_PAUSE))
				 	{ 	
						MessageToPlayer.uMID = MSGID_PLAYER_STOP;
						err = OSQPost(mgr_player_Q, &MessageToPlayer);
				 	}	

					
					/* set the state status */
					SetMPPState(MSGID_PLAYER_STOP);
			
					break;
					
				
				/* message to adjust volume */	
				case MSGID_VOLUME_DN:
				case MSGID_VOLUME_UP:
					/* volume control only during audio play */				
					if(MPPState == STATE_PLAY && MPPMode == MODE_AUDIO)
					{
						MessageToPlayer.uMID = pMessage->uMID;
						MessageToPlayer.Param1 = pMessage->Param1;
						err = OSQPost(mgr_player_Q, &MessageToPlayer);
					}
					break;
					
				/* message to terminate all devices */
				case MSGID_TERMINATE_MPP:
    				close_devicecontrol();   			
					break;
					
				/* message to Display file TAG information */
				case MSGID_LCD_TAG:
    				MessageToDisplay.uMID = MSGID_LCD_TAG;
    				MessageToDisplay.Param1 = pMessage->Param1;
    				MessageToDisplay.Param2 = pMessage->Param2;
					err = OSQPost(mgr_display_Q, &MessageToDisplay);						    			
					break;
					
				/* message to update MPP State status */	
				case MSGID_CMD_STATUS:
					SetMPPState(pMessage->Param1);
					break;
					
				default:
					break;		
		}
		
		if(err && APP_TRACE_LEVEL)
		{
			APP_TRACE("thread_mgr_application OSQPost err =%d\n",err);
			ezErrorCheck(1);
		}

	}	
}

/*********************************************************************

	Function:	SetMPPState																			
	
 	Parameters:	None 
																		
 	Return:		None														
																			
 	Description:	Determines the state of the MPP
*********************************************************************/
static void SetMPPState(u32 cmd)
{
	static char buf[16] = "STATE_IDLE";
	
		switch(cmd)
		{
					
			case MSGID_START_DECODE_AUDIO:
				MPPState = STATE_PLAY;
				MPPMode = MODE_AUDIO;
				OSTaskSuspend(THRD_PRIORITY_POLL_MEDIA);
				strcpy(buf,"STATE_PLAY(audio)");
				break;
			
			case MSGID_START_DECODE_VIDEO:
				MPPState = STATE_PLAY;
				MPPMode = MODE_IMAGE;
				OSTaskSuspend(THRD_PRIORITY_POLL_MEDIA);
				strcpy(buf,"STATE_PLAY(video)");
				break;

				
			case MSGID_PLAYER_STOP:
				MPPState = STATE_IDLE;
				strcpy(buf,"STATE_IDLE(stop)");
				break;
			
			case MSGID_STOP_DECODE:
				MPPState = STATE_IDLE;
				OSTaskResume(THRD_PRIORITY_POLL_MEDIA);
				strcpy(buf,"STATE_IDLE(stop_decode)");
				break;

			case MSGID_PLAYER_PAUSE:
				MPPState = STATE_PAUSE;
				strcpy(buf,"STATE_PAUSE");
				break;
		
			case MSGID_PLAYER_RESUME:
				MPPState = STATE_PLAY;
				strcpy(buf,"STATE_PLAY(resume)");
				break;

			/* no change state */	
			case MSGID_LCD_FILESELECT:
				break;
			
			
			default:
				break;
			
		}

		APP_TRACE("%s\n",buf );

}


/*********************************************************************

	Function:	close_devicecontrol																			
	
 	Parameters:	None 
																		
 	Return:		None														
																			
 	Description:	Closes device drivers
*********************************************************************/
static void close_devicecontrol()
{
	APP_TRACE("App: terminate\n");
	
	OSTaskSuspend(THRD_PRIORITY_POLL_MEDIA);

	close_thumbwheel();
	close_lcd();
	close_keypad();

	/*close_uart();*/
	
	adi_ssl_Terminate();
	

	
}









