//
// Copyright (c) Microsoft Corporation.  All rights reserved.
//
//
// Use of this sample source code is subject to the terms of the Microsoft
// license agreement under which you licensed this sample source code. If
// you did not accept the terms of the license agreement, you are not
// authorized to use this sample source code. For the terms of the license,
// please see the license agreement between you and Microsoft or, if applicable,
// see the LICENSE.RTF on your install media or the root of your tools installation.
// THE SAMPLE SOURCE CODE IS PROVIDED "AS IS", WITH NO WARRANTIES OR INDEMNITIES.
//
//
// Copyright (c) Samsung Electronics. Co. LTD.  All rights reserved.
//
/*++
THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF
ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO
THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
PARTICULAR PURPOSE.

Module Name:    module_interface.cpp

Abstract:       Camera module control common code

Functions:


Notes:


--*/

#include <bsp.h>
#include <pm.h>
#include "pmplatform.h"
#include "Module.h"
#include "camera_hal.h"
//#include "s5k6aafx_module.h"
//#include "s5k4eagx_module.h"

#define CAMERA_OV2655

#ifdef CAMERA_OV2655
//#include "OV2655_module.h"
#include "OV2655_module.h"
#endif
#ifdef CAMERA_OV3640
#include "OV3640_module.h"
#endif

// Variables
static MODULE_SENSOR        g_selectedModule    =   UNKNOWN_MODULE;

static CamModule  *g_pCamModule;
static BOOL b_ModuleInit=FALSE;
static BOOL b_ModuleSensorInit=FALSE;

/////////////////////////////////////////////////////////////////////////////////
// This function will select Module to use, so this function should be called before ModuleInit()
void ModuleSelectSensor(MODULE_SENSOR SensorID)
{
    DBGMSG(CAMC_FUNC, (TEXT("+%s(SensorID=%d)\r\n"), _T(__FUNCTION__), SensorID));

    MODULE_STATUS ModStatus = MOD_STATUS_SUCCESS;

    // On ModuleInit(), the selected module will be initialized
    if( (SensorID == SYSLSI_OV3640) ||
        (SensorID == SYSLSI_S5K6AAFX) ||
        (SensorID == SYSLSI_OV2655))
    {
        g_selectedModule = SensorID;
    }
    else
    {
        g_selectedModule = UNKNOWN_MODULE;
    }
}

// copy module data to output buffer
void ModuleGetFormat(MODULE_DESCRIPTOR *outModuleDesc)
{
    if(g_pCamModule)
    {
        g_pCamModule->GetSupportFormat(outModuleDesc);
    }
    else
    {
        return;
    }
}

// Leave Function definition to retain backward compatibility
int ModuleInit()
{
    int Ret;
    DBGMSG(CAMC_FUNC, (TEXT("+%s\n"), _T(__FUNCTION__)));

	RETAILMSG(1, (TEXT("\n\n\n!ModuleInit,g_selectedModule = %d\r\n"),g_selectedModule));

    if(!b_ModuleInit && !g_pCamModule)
    {
        switch(g_selectedModule)
        {
		RETAILMSG(1, (TEXT("g_selectedModule = %d\r\n"),g_selectedModule));

        case SYSLSI_S5K6AAFX:
//           g_pCamModule = new S5K6AAFX();
        break;
        case SYSLSI_OV3640:
		#ifdef CAMERA_OV3640
		RETAILMSG(1, (TEXT("ModuleInit: OV3640()\r\n")));
        	g_pCamModule = new OV3640();
		#endif
		break;
        case SYSLSI_OV2655:
			//#ifdef CAMERA_OV2655
			RETAILMSG(1, (TEXT("ModuleInit: OV2655()\r\n")));
        		g_pCamModule = new OV2655();
			//#endif
        break;

        default:
            g_pCamModule=NULL;
            Ret=FALSE;
        }
    }
    if(g_pCamModule)
    {
        g_pCamModule->Init();
        b_ModuleInit=TRUE;
        Ret=TRUE;
    }
    else
    {
        Ret=FALSE;
    }

    DBGMSG(CAMC_FUNC, (TEXT("-%s\n"), _T(__FUNCTION__)));
    return Ret;
}

void ModuleDeinit()
{
    DBGMSG(CAMC_FUNC, (TEXT("+%s\n"), _T(__FUNCTION__)));

    g_pCamModule->Deinit();
    b_ModuleInit=FALSE;
    b_ModuleSensorInit=FALSE;
    if(g_pCamModule)
    {
        delete g_pCamModule;
        g_pCamModule=NULL;
    }

    DBGMSG(CAMC_FUNC, (TEXT("-%s\n"), _T(__FUNCTION__)));
}

// This will write command to Camera Module through I2C interface
int  ModuleWriteBlock()
{
    int bRet=TRUE;
    DBGMSG(CAMC_FUNC, (TEXT("+%s\n"), _T(__FUNCTION__)));
    if(g_pCamModule->InitSensor()!= MOD_STATUS_SUCCESS)
    {
        bRet=FALSE;
    }
    b_ModuleSensorInit=TRUE;
    DBGMSG(CAMC_FUNC, (TEXT("-%s=%d\n"), _T(__FUNCTION__), bRet));

    return bRet;
}

int  ModulePrepare()
{
    int bRet=TRUE;
    DBGMSG(CAMC_FUNC, (TEXT("+%s\n"), _T(__FUNCTION__)));
    if(g_pCamModule->SensorPrepare()!= MOD_STATUS_SUCCESS)
    {
        bRet=FALSE;
    }
    DBGMSG(CAMC_FUNC, (TEXT("-%s=%d\n"), _T(__FUNCTION__), bRet));

    return bRet;
}

int  ModuleStart()
{
    int bRet=TRUE;
	RETAILMSG(1, (TEXT("ModuleStart()\r\n")));
    DBGMSG(CAMC_FUNC, (TEXT("+%s\n"), _T(__FUNCTION__)));
    if(g_pCamModule->SensorStart()!= MOD_STATUS_SUCCESS)
    {
        bRet=FALSE;
    }
    DBGMSG(CAMC_FUNC, (TEXT("-%s=%d\n"), _T(__FUNCTION__), bRet));

    return bRet;
}

int  ModuleCapturePrepare()
{
    int bRet=TRUE;
    DBGMSG(CAMC_FUNC, (TEXT("+%s\n"), _T(__FUNCTION__)));

    if(g_pCamModule->StartCapture()!= MOD_STATUS_SUCCESS)
    {
        bRet=FALSE;
    }

    DBGMSG(CAMC_FUNC, (TEXT("-%s=%d\n"), _T(__FUNCTION__), bRet));

    return bRet;
}

int  ModuleCaptureStart()
{
    int bRet=TRUE;
    DBGMSG(CAMC_FUNC, (TEXT("+%s\n"), _T(__FUNCTION__)));

    if(g_pCamModule->StopCapture()!= MOD_STATUS_SUCCESS)
    {
        bRet=FALSE;
    }

    DBGMSG(CAMC_FUNC, (TEXT("-%s=%d\n"), _T(__FUNCTION__), bRet));

    return bRet;
}


int ModuleSetFormatSize(CAMIF_OPERATION_MODE OPMode, CAMIF_IMG_SIZE imageSize)
{
    MODULE_STATUS bRet;

    DBGMSG(CAMC_FUNC, (TEXT("+%s\n"), _T(__FUNCTION__)));
    bRet = g_pCamModule->SetOperationMode(OPMode);
    bRet = g_pCamModule->SetFormatSize(imageSize);
    DBGMSG(CAMC_FUNC, (TEXT("-%s\n"), _T(__FUNCTION__)));

    return (int)bRet;
}

MODULE_STATUS ModuleSetPower(MODULE_PWR_STATUS NewPower)
{
    DBGMSG(CAMC_FUNC, (TEXT("+%s\n"), _T(__FUNCTION__)));

    MODULE_STATUS ModStatus = MOD_STATUS_SUCCESS;

    if ( NewPower == MOD_PWR_STATUS_ON )
    {
        // Configure default pin states before power up sequence
        //ModuleConfigurePinMux();
        ModStatus = g_pCamModule->Power(TRUE);
    }
    else if ( NewPower == MOD_PWR_STATUS_OFF )
    {
        ModStatus = g_pCamModule->Power(FALSE);
    }
    else if ( NewPower == MOD_PWR_STATUS_STANDBY )
    {
        ModStatus = g_pCamModule->Standby(TRUE);
    }
    else if ( NewPower == MOD_PWR_STATUS_WAKEUP )
    {
        ModStatus = g_pCamModule->Standby(FALSE);
    }
    else if ( NewPower == MOD_PWR_STATUS_RESET_ACTIVE )
    {
        ModStatus = g_pCamModule->Reset(TRUE);
    }
    else if ( NewPower == MOD_PWR_STATUS_RESET_DEACTIVE )
    {
        ModStatus = g_pCamModule->Reset(FALSE);
    }

    return ModStatus;
}
