/*******************************************************************************
 * (c) Copyright 2015 Microsemi Corporation.  All rights reserved.
 *
 *
 *
 * SVN $Revision: $
 * SVN $Date: $
 */

#ifndef DM_H_
#define DM_H_

#include <api_oam_sdk/performance_monitoring/inc/pm_dm.h>
#include <api_oam_sdk/performance_monitoring/src/pm_config.h>
#include <api_oam_sdk/performance_monitoring/src/pm_types.h>
#include <api_oam_sdk/table_access/inc/table_types.h>
#include "egl_types.h"

typedef struct dmStatsEntry_s {
	uint32_t	fDPktCntr;
	uint32_t	fDErrCntr;
	uint32_t	fDVErrCntr;
	uint32_t	lastDelay;
	uint32_t	lastVar;
	uint32_t	minFD;
    uint32_t	maxFD;
    uint32_t	sumFDUpp;
    uint32_t	sumFDLow;
    uint32_t	minFDV;
    uint32_t	maxFDV;
    uint32_t	sumFDVUpp;
    uint32_t	sumFDVLow;
} dmStatsEntry_t;

typedef struct dmStatsBinsEntry_s {
	uint32_t	fDPktCntr;
	uint32_t	fDErrCntr;
	uint32_t	fDVErrCntr;
    uint32_t	fDBukt0;
    uint32_t	fDBukt1;
    uint32_t	fDBukt2;
    uint32_t	fDBukt3;
    uint32_t	fDVBukt0;
    uint32_t	fDVBukt1;
    uint32_t	fDVBukt2;
    uint32_t	fDVBukt3;
} dmStatsBinsEntry_t;

typedef struct
{
	uint32_t		index;						// The index for the current Measurement Interval for this PM session
	dateAndTime_t	startTime;					// The time that the current Measurement Interval started
	timeInterval_t	elapsedTime;				// The time that the current Measurement Interval has been running, in 0.01 seconds
	uint32_t		frameDelayTwoWayMin;		// The minimum two-way frame delay calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayTwoWayMax;		// The maximum two-way frame delay calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayTwoWayAvg;		// The average two-way frame delay calculated by this MEP for this Measurement Interval
#if NOT_SUPPORTED_YET
	uint32_t		frameDelayForwardMin;		// The minimum one-way frame delay in the forward direction calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayForwardMax;		// The maximum one-way frame delay in the forward direction calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayForwardAvg;		// The average one-way frame delay in the forward direction calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayBackwardMin;		// The minimum one-way frame delay in the backward direction calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayBackwardMax;		// The maximum one-way frame delay in the backward direction calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayBackwardAvg;		// The average one-way frame delay in the backward direction calculated by this MEP for this Measurement Interval
	uint32_t		ifdvForwardMin;				// The minimum one-way inter-frame delay interval in the forward direction calculated by this MEP for this Measurement Interval
	uint32_t		ifdvForwardMax;				// The maximum one-way inter-frame delay interval in the forward direction calculated by this MEP for this Measurement Interval
	uint32_t		ifdvForwardAvg;				// The average one-way inter-frame delay interval in the forward direction calculated by this MEP for this Measurement Interval
	uint32_t		ifdvBackwardMin;			// The minimum one-way inter-frame delay interval in the backward direction calculated by this MEP for this Measurement Interval
	uint32_t		ifdvBackwardMax;			// The maximum one-way inter-frame delay interval in the backward direction calculated by this MEP for this Measurement Interval
	uint32_t		ifdvBackwardAvg;			// The average one-way inter-frame delay interval in the backward direction calculated by this MEP for this Measurement Interval
#endif
	uint32_t		ifdvTwoWayMin;				// The minimum two-way inter-frame delay interval calculated by this MEP for this Measurement Interval
	uint32_t		ifdvTwoWayMax;				// The maximum two-way inter-frame delay interval calculated by this MEP for this Measurement Interval
	uint32_t		ifdvTwoWayAvg;				// The average two-way inter-frame delay interval calculated by this MEP for this Measurement Interval
#if NOT_SUPPORTED_YET
	uint32_t		frameDelayRangeForwardMax;	// The maximum one-way frame delay range in the forward direction calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayRangeForwardAvg;	// The average one-way frame delay range in the forward direction calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayRangeBackwardMax;	// The maximum one-way frame delay range in the backward direction calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayRangeBackwardAvg;	// The average one-way frame delay range in the backward direction calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayRangeTwoWayMax;	// The maximum two-way frame delay range calculated by this MEP for this Measurement Interval
	uint32_t		frameDelayRangeTwoWayAvg;	// The average two-way frame delay range calculated by this MEP for this Measurement Interval
#endif
	gauge32_t		soamPdusSent;				// contains the count of the number of SOAM PDUs sent during this Measurement Interval
	gauge32_t		soamPdusReceived;			// contains the count of the number of SOAM PDUs PDUs received in this Measurement Interval
	bool			suspect;					// Whether the Measurement Interval has been marked as suspect
} dmStatsReduced_t;

void dmReadStats(pmNum_t pmNum, dmStatsEntry_t *delayStatEntry);

void dmReadStatsBins(pmNum_t pmNum, dmStatsBins_t dmStatsBinsEntry);

void dmClearStats(pmNum_t pmNum);

void addDMSvcToLMep(lMepNum_t lMepNum,
		rMepNum_t rMepNum, uint8_t pmInterval,
		uint32_t delayThresh, uint32_t delayVarThresh, uint8_t prio,
		txTemplateEntry_t *txDMMTempl, pmNum_t pmNum, iFace_t iFace);

void removeDMSvc(pmNum_t pmNum);

void dmSvcEnable(pmNum_t pmNum, bool enable);

#ifdef PM_RAM_HISTORY
void copyDmHistoryStatsToDmHistoryStatsReduced(dmStats_t *historyStats, dmStatsReduced_t *historyStatsReduced);

void copyDmHistoryStatsReducedToDmHistoryStats(dmStatsReduced_t *historyStatsReduced, dmStats_t *historyStats);

int readDmHistoryStats(pmNum_t pmNum, uint32_t statsIndex, dmStats_t *historyStats, dmStatsBins_t historyStatsBins);

int writeDmHistoryStats(pmNum_t pmNum, dmStats_t *historyStats, dmStatsBins_t historyStatsBins);

void clearDmHistory(pmNum_t pmNum);
#endif

#endif /* DM_H_ */
