/****************************************************************************/
/* Copyright 2003-2012 MBARI						    */
/****************************************************************************/
/* Summary  : Main Routine for BEDS on Persistor CF2			    */
/* Filename : beds.c                                                        */
/* Author   : Robert Herlien (rah)					    */
/* Project  : BEDS (Benthic Event Detection System)			    */	
/* Revision : 1.0							    */
/* Created  : 04/18/2012						    */
/*									    */
/* MBARI provides this documentation and code "as is", with no warranty,    */
/* express or implied, of its quality or consistency. It is provided without*/
/* support and without obligation on the part of the Monterey Bay Aquarium  */
/* Research Institute to assist in its use, correction, modification, or    */
/* enhancement. This information should not be published or distributed to  */
/* third parties without specific written permission from MBARI.            */
/*									    */
/****************************************************************************/
/* Modification History:						    */
/* 18apr2012 rah - created						    */
/* $Log$
 */
/****************************************************************************/

#include <mbariTypes.h>		/* MBARI type definitions		*/
#include <mbariConst.h>		/* MBARI constants			*/
#include <cfxpico.h>		/* Persistor PicoDOS Definitions	*/
#include <beds.h>		/* BEDS general definitions		*/	
#include <io.h>			/* BEDS I/O definitions			*/
#include <serial.h>		/* BEDS serial I/O definitions		*/
#include <file.h>		/* BEDS file I/O definitions		*/
#include <config.h>		/* BEDS configuration			*/
#include <bedsCmd.h>		/* BEDS Command line processor		*/
#include <syslog.h>		/* System logger			*/
#include <adc.h>		/* BEDS Analog Module			*/
#include <twim.h>		/* BEDS software I2C			*/
#include <watch.h>		/* BEDS watch cycle			*/
#include <event.h>		/* BEDS event cycle			*/
#include <spi.h>		/* BEDS SPI module			*/
#include <clock.h>		/* BEDS Clock module			*/
#include <modem.h>		/* BEDS Acoustic modem routines		*/

#include <stddef.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>

/* From Invensense MotionApps Stack */
#include "log.h"
#undef MPL_LOG_TAG
#define MPL_LOG_TAG "uMPL-main"

// MPL interface
#include "ml.h"
#include "mldl.h"
#include "umpl-states.h"


/********************************/
/*	External Data		*/
/********************************/

Extern time_t	startTime;


/********************************/
/*	Module Local Data	*/
/********************************/

#ifdef WATCHDOG
// This definition is the key to using the WDT on the Persistor CF2
short	CustomSYPCR = WDT26s | HaltMonEnable | BusMonEnable | BMT32;
#endif


/************************************************************************/
/* Function    : platform_init						*/
/* Purpose     : Initialize hardware-specific platform stuff		*/
/* Inputs      : None							*/
/* Outputs     : None							*/
/************************************************************************/
MLocal void platform_init(void)
{
    /* Note - check for errors!	*/

    ioInit();			/* Initialize I/O system and ticker	*/
    serInit();			/* Initialize serial I/O module		*/
    fileInit();			/* Initialize file I/O module		*/
    sysLogInit();		/* Initialize sysLogger			*/

    twimInit();			/* Initialize I2C interface		*/
    spiInit();			/* Initialize the SPI module		*/
    adcInit();			/* Initialize the ADC module		*/
    parseConfigFile(CFG_FILE);	/* Need user vars for some of below	*/
    clkInit();			/* Initialize the clock module		*/
    watchInit();		/* Initialize the watch cycle module	*/
    eventInit();		/* Initialize the event cycle module	*/
    modemInit();
#ifdef WATCHDOG
    TickleSWSR();		/* Start the watchdog timer		*/
#endif

    _MPL_ENABLE_LOG(MPL_LOG_INFO, true);

} /* platform_init() */


/************************************************************************/
/* Function    : main							*/
/* Purpose     : Main entry point					*/
/* Inputs      : argc, argv						*/
/* Outputs     : None							*/
/* Comments    : Never returns						*/
/************************************************************************/
int main(int argc, char **argv)
{
#pragma unused(argc, argv)
    time_t	now;
    inv_error_t result = INV_SUCCESS;

    // Identify the progam and build
    printf("\nProgram: %s: %s %s \n", __FILE__, __DATE__, __TIME__);
    // Identify the device and its firmware
    printf("Persistor CF%d SN:%ld   BIOS:%d.%02d   PicoDOS:%d.%02d\n", CFX,
	   BIOSGVT.CFxSerNum, BIOSGVT.BIOSVersion, BIOSGVT.BIOSRelease, 
	   BIOSGVT.PICOVersion, BIOSGVT.PICORelease);

    platform_init();

    if (time(&now) < startTime)
    {
	modemOff();
	sysLogPrintf("Sleeping until %s\n", asctime(gmtime(&startTime)));
    }

    CIOiflush();
    while(time(&now) < startTime)
    {
	if (kbhit())
	{
	    sysLogPrintf("Woke due to keyboard char\n");
	    break;
	}
	ioSleep(TICKS_PER_SECOND);	/* Sleep until start time*/
#ifdef WATCHDOG
	TickleSWSR();			/* Keep watchdog running */
#endif
    }

    //Initialize and start MPU6000
    ioNavPwr(TRUE);
//    RTCDelayMicroSeconds(500000);

    MPL_LOGI(INV_VERSION "\n");
    sysLog(INV_VERSION);

    result = umplInit(NULL);
    if (result != INV_SUCCESS)
        MPL_LOGE("umplInit Error %d\n",result);

    sysLogPrintf("umplInit rtn code = %hd", (short)result);

    result = umplStartMPU();
    sysLogPrintf("umplStartMPU rtn code = %hd", (short)result);

    if (result != INV_SUCCESS)
	MPL_LOGE("umplStartMPU Error %d\n",result);

    sysLog("Entering main processing loop");

    watchCycle();

    /* Should never get here	*/
    BIOSReset();			// full hardware reset
    return(0);

} //____ main() ____//
