/****************************************************************************
 *  F i l e   D a t a                                                        
 *  $Id: TRK_Tracker_INFN.c,v 1.80 2005/03/20 18:27:29 sebastiani Exp $
 *  $Revision: 1.80 $
 *  $Date: 2005/03/20 18:27:29 $
 *  $RCSfile: TRK_Tracker_INFN.c,v $
 *                                                                           
 ****************************************************************************
 *  S W   D e v e l o p m e n t   E n v i r o n m e n t                      
 *                                                                           
 *  $Author: sebastiani $
 *               :                                                           
 ****************************************************************************
 *  U p d a t i n g                                                          

 *  $Log: TRK_Tracker_INFN.c,v $
 *  Revision 1.80  2005/03/20 18:27:29  sebastiani
 *  TRK calibration: many bugs found and fixed in TRK_Check (many & , << , >> errors!)
 *
 *  Revision 1.79  2005/03/06 14:54:46  sebastiani
 *  version running on 06 03 2005
 *
 *  Revision 1.78  2005/02/24 17:52:22  sebastiani
 *  PWR_CMD2PSB accept more params cause bugfixing (2) PRH_ARR_PSB_COMMANDS introduced instead of PRH_VAR_xxxxx
 *
 *  Revision 1.77  2005/02/22 18:09:25  sebastiani
 *  various bugfixes
 *
 *  Revision 1.76  2005/02/21 14:26:01  sebastiani
 *  TSB bugfixes.
 *
 *  Revision 1.75  2005/02/21 08:58:29  sebastiani
 *  all log comments completed
 *
 *  Revision 1.74  2004/12/22 09:35:36  sebastiani
 *  CH_PARAMBUF_SET_ATO_ETO(TRK_TRAILER_PRG[i],8,0) bugfix
 *  should be 0,8 instead
 *
 *  Revision 1.73  2004/12/21 14:16:35  sebastiani
 *  *** empty log message ***
 *
 *  Revision 1.72  2004/12/20 14:02:04  faber
 *  @LOG entry introduced in all ALM_WriteLog occurrences
 *
 *  Revision 1.70  2004/12/15 09:36:23  sebastiani
 *  TRK_WRITE2RAM removed: DAQ_NO_STORE_RAM used instead; TRK_Send_ReadCalibrationCmd and TRK_Assemble_ReadCalibrationCmd introduced; many other fixes and flow little changes in the calibration
 *
 *  Revision 1.69  2004/11/19 15:41:50  sebastiani
 *  *** empty log message ***
 *
 *  Revision 1.68  2004/11/19 15:14:52  sebastiani
 *  PRH_EXTERN_{VAR,ARR,TABLE} removed and put them on the autogenerated parameter heeader file
 *
 *  Revision 1.67  2004/10/08 07:27:23  sebastiani
 *  *** empty log message ***
 *
 *  Revision 1.66  2004/10/06 16:40:23  faber
 *  Sensor board reading is fixed size in MM (always 13 words)
 *
 *  Revision 1.65  2004/09/28 15:36:25  sebastiani
 *  interrupt manager fix
 *
 *  Revision 1.64  2004/09/27 15:42:43  alfarano
 *  tracker sensor board functions
 *
 *  Revision 1.63  2004/09/22 15:54:54  alfarano
 *  S4 functions
 *
 *  Revision 1.62  2004/09/17 15:52:00  faber
 *  fix command queue Cmd2Fe/Fe2Daq right invocation for Test funcion inf TOF and TRG
 *
 *  Revision 1.61  2004/09/17 15:01:00  faber
 *  LU_INFN_LOG flags fixing
 *
 *  Revision 1.60  2004/09/13 14:16:53  faber
 *  ErrorHandler for TOF/TRG + Test function TOF/TRG
 *
 *  Revision 1.59  2004/08/31 09:13:20  sebastiani
 *  fix warning
 *
 *  Revision 1.58  2004/08/31 09:08:35  sebastiani
 *  fix warning
 *
 *  Revision 1.57  2004/08/27 13:30:39  alfarano
 *  cvs header
 *
 *  Revision 1.1  2003/10/03 16:12:26  faber
 *  *** empty log message ***
 *
 *                                                                           
 *****************************************************************************/
/*============================= Include File ================================*/


#include <src/INFN/LU_SourceFileID_INFN.h>
#define __FILEID__ _TRK_Tracker_INFN__c
#include <src/INFN/PRH_ParamHandler_INFN.h>
#include <src/INFN/LU_LogUtility_INFN.h>
#include <src/INFN/PRH_ParamHandler_INFN_auto.h>
LU_DECL_MASK();

#include <src/INFN/CM_Common_INFN.h>
#include <src/INFN/TRK_Tracker_INFN.h>
#include <src/INFN/CH_CommandHandler_INFN.h>
#include <src/INFN/TRG_Trigger_INFN.h>
#include <src/INFN/RM_RunManager_INFN.h>
#include <src/INFN/KHB_Driver_INFN.h>
#include <src/INFN/HB_HKBuffer_INFN.h>
#include <src/SRAMManager/SRAMDriver/SD_SRAMDriver_p.h>
#include <src/SRAMManager/SRAMPageManager/SM_SRAMPageManager_p.h>
#include <src/FileManager/MMSUManager/FT_MMSUManager_p.h>
#include <src/INFN/HK_Manager_INFN.h>
#include <src/INFN/ALM_Alarm_INFN.h>
#include <src/INFN/MH_ModeHandler_INFN.h>
#include <src/INFN/PWR_PowerHandler_INFN.h>

/*============================ External define ================================*/


DAQ_DECLBUF(TRK_command,1024);
DAQ_DECLBUF(TRK_TempPif0,TRK_MAXTEMPBUFFER);
DAQ_DECLBUF(TRK_TempPif1,TRK_MAXTEMPBUFFER);
DAQ_DECLBUF(TRK_TempPif2,TRK_MAXTEMPBUFFER);
DAQ_DECLBUF(TRK_TempPif3,TRK_MAXTEMPBUFFER);
DAQ_DECLBUF(TRK_daq_reply0,128*1024);
DAQ_DECLBUF(TRK_daq_reply1,128*1024);
DAQ_DECLBUF(TRK_tempbuf,TRK_MAX_LOG_SIZE);


static DAQ_CMD_BUF TRK_NUMBER_DSP[1+2][6];

static DAQ_CMD_BUF TRK_OPMODE_COMP[6];

static DAQ_CMD_BUF TRK_OPMODE_SPEC[6];

static DAQ_CMD_BUF TRK_PROGRAM;

static DAQ_CMD_BUF TRK_TRAILER_PRG[6];

static BOOL   TRK_Bfield_flag=TRUE;

extern BOOL RM_Init_Before_Calib;
/*============================ Global define ================================*/

#define TRK_SKIP_HEADER SM_PKTHEADER_LEN

#define TRK_MASK_BASE_ID CH_TRK_MASK_064
#define TRK_MASK_BASE_OFFSET 64
#define TRK_PROG_ADR_BASE_ID CH_TRK_PROG_ADR_01
#define TRK_LOAD_DATA_BASE_ID CH_TRK_LOAD_DATA_0
#define TRK_HEADER_PRG_BASE_ID CH_TRK_HEADER_PRG_0
#define TRK_START_BASE_ID CH_TRK_START_0
#define TRK_CALIB_ADR_BASE_ID CH_TRK_CALIB_ADR_0_1_101
#define TRK_CALIB_ADR_BASE_OFFSET 101
#define TRK_SET_CALIB_NORMAL_BASE_ID CH_TRK_SET_CALIB_NORMAL_0
#define TRK_SET_CALIB_SPECIAL_BASE_ID CH_TRK_SET_CALIB_SPECIAL_0
#define TRK_EVENT_ACQ_BASE_ID CH_TRK_EVENT_ACQ_0
#define TRK_READ_HEADER_BASE_ID CH_TRK_READ_HEADER_0
#define TRK_READ_LADDER1_BASE_ID CH_TRK_READ_LADDER1_0
#define TRK_READ_LADDER2_BASE_ID CH_TRK_READ_LADDER2_0
#define TRK_READ_LADDER3_BASE_ID CH_TRK_READ_LADDER3_0
#define TRK_READ_INPUT_BASE_ID CH_TRK_READ_INPUT_0
#define TRK_WRITE_DMTEST_DSP_BASE_ID CH_TRK_WRITE_DMTEST_DSP_0
#define TRK_WRITE_PMTEST_DSP_BASE_ID CH_TRK_WRITE_PMTEST_DSP_0
#define TRK_WRITE_PROGTEST_DSP_BASE_ID CH_TRK_WRITE_PROGTEST_DSP_0
#define TRK_READ_DMTEST_DSP_BASE_ID CH_TRK_READ_DMTEST_DSP_0
#define TRK_READ_PMTEST_DSP_BASE_ID CH_TRK_READ_PMTEST_DSP_0
#define TRK_RESET_DSP_BASE_ID CH_TRK_RESET_DSP_0





/*============================== global types  ==============================*/



/*=========================== Structure define ==============================*/


/*============================ Enumerate define =============================*/


UINT32 TRK_ALARM_MASK[2];
static UINT32 TRK_status;
static UINT32 TRK_calib_used;

static void TRK_Init_TRK_NUMBER_DSP() {
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,1,0);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,1,1);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,1,2);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,1,3);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,1,4);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,1,5);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,2,0);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,2,1);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,2,2);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,2,3);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,2,4);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_TAB(TRK_NUMBER_DSP,2,5);
}

status_code TRK_Get_TRK_NUMBER_DSP(BYTE i,BYTE j,DAQ_CMD_BUF **p) {
  *p= & (TRK_NUMBER_DSP[i][j]);
}

static void TRK_Init_TRK_OPMODE_SPEC() {
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_SPEC,0);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_SPEC,1);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_SPEC,2);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_SPEC,3);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_SPEC,4);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_SPEC,5);
}

status_code TRK_Get_TRK_OPMODE_SPEC(BYTE i,DAQ_CMD_BUF **p) {
  *p= & (TRK_OPMODE_SPEC[i]);
}

static void TRK_Init_TRK_OPMODE_COMP() {
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_COMP,0);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_COMP,1);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_COMP,2);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_COMP,3);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_COMP,4);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_OPMODE_COMP,5);
}

static void TRK_Init_TRK_PROGRAM() {
  DAQ_INIT_BUF_FROM_PARAMBUF(TRK_PROGRAM);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_TRAILER_PRG,0);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_TRAILER_PRG,1);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_TRAILER_PRG,2);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_TRAILER_PRG,3);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_TRAILER_PRG,4);
  DAQ_INIT_BUF_FROM_PARAMBUF_AS_ARR(TRK_TRAILER_PRG,5);
}


status_code TRK_Get_TRK_OPMODE_COMP(BYTE i,DAQ_CMD_BUF **p) {
  *p= & (TRK_OPMODE_COMP[i]);
}

void TRK_Init_ParamBuffers() {
  TRK_Init_TRK_PROGRAM();
  TRK_Init_TRK_NUMBER_DSP();  
  TRK_Init_TRK_OPMODE_COMP();
  TRK_Init_TRK_OPMODE_SPEC();
}


status_code TRK_Init_ETOATO()
{
  int i;

  for(i=0; i < 6; i++)
    CH_SetAtoEto(TRK_RESET_DSP_BASE_ID+i,2,3);
  
  for(i=0; i < 15; i++)
    CH_SetAtoEto(TRK_PROG_ADR_BASE_ID+i,2,3);

  for(i=0; i < 6; i++)
    CH_SetAtoEto(TRK_LOAD_DATA_BASE_ID+i,0,8);

  for(i=0; i < 6; i++)
    CH_SetAtoEto(TRK_HEADER_PRG_BASE_ID+i,0,8);

  
  for(i=0; i < 6; i++)
    {
      CH_PARAMBUF_SET_ATO_ETO(TRK_NUMBER_DSP[1][i],2,3);
      CH_PARAMBUF_SET_ATO_ETO(TRK_NUMBER_DSP[2][i],2,3);
      CH_PARAMBUF_SET_ATO_ETO(TRK_OPMODE_COMP[i],2,3);
      CH_PARAMBUF_SET_ATO_ETO(TRK_OPMODE_SPEC[i],2,3);
      CH_PARAMBUF_SET_ATO_ETO(TRK_TRAILER_PRG[i],0,8);
    }

  for(i=0; i < 6; i++)
    {
      CH_SetAtoEto(TRK_WRITE_DMTEST_DSP_BASE_ID+i,2,3);
      CH_SetAtoEto(TRK_WRITE_PMTEST_DSP_BASE_ID+i,2,3);
      CH_SetAtoEto(TRK_READ_DMTEST_DSP_BASE_ID+i,2,3);
      CH_SetAtoEto(TRK_READ_PMTEST_DSP_BASE_ID+i,2,3);
      CH_SetAtoEto(TRK_WRITE_PROGTEST_DSP_BASE_ID+i,0,0);
    }

  for(i=0; i < 126; i++)
    CH_SetAtoEto(TRK_CALIB_ADR_BASE_ID+i,2,3);
  
  CH_SetAtoEto(CH_TRK_TESTWORD_ADR,2,3);

  for(i=0; i < 6; i++)
    {
      CH_SetAtoEto(TRK_SET_CALIB_NORMAL_BASE_ID+i,2,3);
      CH_SetAtoEto(TRK_SET_CALIB_SPECIAL_BASE_ID+i,2,3);
      CH_SetAtoEto(TRK_EVENT_ACQ_BASE_ID+i,2,9);
      CH_SetAtoEto(TRK_READ_INPUT_BASE_ID+i,2,8);
      CH_SetAtoEto(TRK_READ_HEADER_BASE_ID+i,2,4);
    }
  
  for(i=0; i < 192; i++)
    CH_SetAtoEto(TRK_MASK_BASE_ID+i,2,3);
  
  CH_SetAtoEto(CH_TRK_GENERAL_RESET,2,3);
  CH_SetAtoEto(CH_TRK_FLASH_ON,5,6);
  CH_SetAtoEto(CH_TRK_FLASH_OFF,2,3);
  CH_SetAtoEto(CH_TRK_RESET_FLASH,2,3);

  for(i=0; i < 6; i++)
    {
      CH_SetAtoEto(TRK_START_BASE_ID+i,2,3);  
      CH_SetAtoEto(TRK_READ_LADDER1_BASE_ID+i,2,8);
      CH_SetAtoEto(TRK_READ_LADDER2_BASE_ID+i,2,8);
      CH_SetAtoEto(TRK_READ_LADDER3_BASE_ID+i,2,8);
    }
  
  CH_SetAtoEto(CH_TRK_READ_CR,2,3);
  CH_SetAtoEto(CH_TB_GIVE_ME_TRIGGER,0,1);
}

status_code TRK_Get_CalibUsed(UINT32 *calib_used)
{
  *calib_used = TRK_calib_used;
}

status_code TRK_Init() 
{
  DAQ_BUFFER_INIT(TRK_TempPif0);
  DAQ_BUFFER_INIT(TRK_TempPif1);
  DAQ_BUFFER_INIT(TRK_TempPif2);
  DAQ_BUFFER_INIT(TRK_TempPif3);
  DAQ_BUFFER_INIT(TRK_daq_reply0);
  DAQ_BUFFER_INIT(TRK_daq_reply1);
  DAQ_BUFFER_INIT(TRK_tempbuf);
  memset(TRK_ALARM_MASK,0,sizeof(TRK_ALARM_MASK));
  TRK_Init_ParamBuffers();
  TRK_Init_ETOATO();

  return CM_RC_SUCCESSFUL;
}

status_code TRK_InitTracker()
{
  return CM_RC_SUCCESSFUL;
}

status_code TRK_CheckPacket(DAQ_CMD_BUF *buf,DAQ_FE idaqfe)
{
  status_code status;
  BYTE *take,tmp;
  UINT32 buflen;
  UINT16 temp_get,EVENT_CAL,FLAG;
  UINT16 PED_L[4],SIG_L[4],BAD_L[4];
  UINT16 cond,i,j;
  
#define TRK_DSP_CALIBPKT_SIZE (6364*2)
#define TRK_DSPCALIBPKT_REMAIN (6352*2)
  
  take = buf->buf;
  buflen = buf->len;
  
  status = CM_RC_INVALID_BUFFER_SIZE;
  
  if(buflen < TRK_SKIP_HEADER)
    LU_EXIT_IFERROR(status);
  
  take+=TRK_SKIP_HEADER;
  buflen-=TRK_SKIP_HEADER;
  
  for(j=0; j < 6; j++)
    {
      if (PRH_TAB_TRK_DSP_OK[idaqfe][j])
	{
	  if(buflen < TRK_DSP_CALIBPKT_SIZE)
	    LU_EXIT_IFERROR(status);
	  
	  buflen -= TRK_DSP_CALIBPKT_SIZE;
	  take+=6;
	  CM_READ_BE_UINT16(take,temp_get,tmp);
	  EVENT_CAL = (temp_get & 0x01FF) << 1;
	  CM_READ_BE_UINT16(take,temp_get,tmp);
	  EVENT_CAL |= (temp_get & 0x8000) >> 15;
	  PED_L[1] = (temp_get & 0x0FFC)>>2;
	  CM_READ_BE_UINT16(take,temp_get,tmp);
	  PED_L[2] = (temp_get & 0x7FE0)>>5;
	  PED_L[3] = (temp_get & 3) << 8;
	  CM_READ_BE_UINT16(take,temp_get,tmp);
	  PED_L[3] |=(temp_get & 0xFF00) >> 8;
	
	  SIG_L[1] = (temp_get & 0x001F) << 5;
	  CM_READ_BE_UINT16(take,temp_get,tmp);
	  SIG_L[1] |= (temp_get & 0xF800) >> 11;
	  SIG_L[2] = (temp_get & 0x00FF) << 2;
	  CM_READ_BE_UINT16(take,temp_get,tmp);
	  SIG_L[2] |= (temp_get & 0xC000) >> 14;
	  SIG_L[3] = (temp_get & 0x07FE) >> 1;
	  CM_READ_BE_UINT16(take,temp_get,tmp);
	  BAD_L[1] = (temp_get & 0x3FF0) >> 4;
	  BAD_L[2] = (temp_get & 0x0001) << 9; 
	  CM_READ_BE_UINT16(take,temp_get,tmp);
	  BAD_L[2] |= (temp_get & 0xFF80) >> 7;
	  BAD_L[3] = (temp_get & 0x000F) << 6;
	  CM_READ_BE_UINT16(take,temp_get,tmp);
	  BAD_L[3] |= (temp_get & 0xFC00) >> 10;
	  FLAG = (temp_get & 0060) >> 5;

	  take+=TRK_DSPCALIBPKT_REMAIN;
	  cond = 1;

	  if (!EVENT_CAL && !FLAG)
	    {
	      if (idaqfe == DAQ_FE_TRK_1)
		{
		  for (i=1; i < 4; i++)
		    cond = cond && (PED_L[i] > (PRH_TAB_TRK_PED_MIN_0[i-1][j] / 4 ));
	      
		  for (i=1; i < 4; i++)
		    cond = cond && (PED_L[i] < (PRH_TAB_TRK_PED_MAX_0[i-1][j] / 4 ));
	      
		  for (i=1; i < 4; i++)
		    cond = cond && (SIG_L[i] > (PRH_TAB_TRK_SIG_MIN_0[i-1][j]  ));
	      
		  for (i=1; i < 4; i++)
		    cond = cond && (SIG_L[i] < (PRH_TAB_TRK_SIG_MAX_0[i-1][j]  ));
	      
		  for (i=1; i < 4; i++)
		    cond = cond && (BAD_L[i] < (PRH_TAB_TRK_BAD_MAX_0[i-1][j]  ));
		}
	      else
		{
		  for (i=1; i < 4; i++)
		    cond = cond && (PED_L[i] > (PRH_TAB_TRK_PED_MIN_1[i-1][j] / 4 ));
	      
		  for (i=1; i < 4; i++)
		    cond = cond && (PED_L[i] < (PRH_TAB_TRK_PED_MAX_1[i-1][j] / 4 ));
	      
		  for (i=1; i < 4; i++)
		    cond = cond && (SIG_L[i] > (PRH_TAB_TRK_SIG_MIN_1[i-1][j]  ));
	      
		  for (i=1; i < 4; i++)
		    cond = cond && (SIG_L[i] < (PRH_TAB_TRK_SIG_MAX_1[i-1][j]  ));
	      
		  for (i=1; i < 4; i++)
		    cond = cond && (BAD_L[i] < (PRH_TAB_TRK_BAD_MAX_1[i-1][j]  ));
		}      
	      if (cond==0)
		break;
	    }
	  else
	    {
	      cond=0;
	      /*@LOG TRK_CheckPacket: cond set to zero. - FLAG */
	      LU_INFN_LOG(LU_DEBUG_TRACE,LU_MASK(__FILEID__),__FILEID__,__LINE__,FLAG);
	      /*@LOG TRK_CheckPacket: cond set to zero. - EVENT_CAL */
	      LU_INFN_LOG(LU_DEBUG_TRACE,LU_MASK(__FILEID__),__FILEID__,__LINE__,EVENT_CAL);
	      break;
	    }
	}
    }
  /*@LOG TRK_CheckPacket end -  cond  */
  LU_INFN_LOG(LU_DEBUG_TRACE,LU_MASK(__FILEID__),__FILEID__,__LINE__,cond);
  return ((cond == 1) ? CM_RC_SUCCESSFUL : CM_RC_UNSATISFIED);
}

status_code TRK_Initialization()
{
  status_code status=CM_RC_SUCCESSFUL;
  int trk_loop_ini;
  int j,i,k,x;
  DAQ_FE idaqfe;
  UINT16 alarm_reg;
  DAQ_CMD_BUF* auto_buf;

  TRK_status = 1;
  trk_loop_ini = 1; 

  DAQ_Format_CMD_Empty(&TRK_TempPif0);

  status = DAQ_ResetPIF(DAQ_DEFAULT_ETO_TICS,DAQ_MAX_DTO_TICS,SM_DAQSETUP,HB_PKTTYPE_TRK_INIT);

  for( i=0,idaqfe = DAQ_FE_TRK_1; idaqfe <= DAQ_FE_TRK_2; idaqfe++,i++)
    {
      TRK_ALARM_MASK[i] = 0;  j = 0;

      while (j < 6)
	{
	  if (!PRH_TAB_TRK_DSP_OK[i][j])
	    TRK_ALARM_MASK[i] |= (1 << j);
	  if (PRH_TAB_TRK_DSP_MASK[i][j])
	    TRK_ALARM_MASK[i] |= (1 << j);
	  
	  j++;
	}
      
      TRK_ALARM_MASK[i] |= 0xc0;
            
      CH_GetBuf(TRK_MASK_BASE_ID+TRK_ALARM_MASK[i]-TRK_MASK_BASE_OFFSET,&auto_buf );
      DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
      CH_GetBuf(CH_TRK_GENERAL_RESET,&auto_buf);
      DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
    }

  status = DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
  LU_EXIT_IFERROR(status);
  status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,DAQ_STORE_MM,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
  LU_EXIT_IFERROR(status); 

  for(i=0, idaqfe = DAQ_FE_TRK_1; idaqfe <= DAQ_FE_TRK_2; idaqfe++,i++)
    {
      DAQ_Format_CMD_Empty(&TRK_TempPif0);
      x = PRH_ARR_TRK_LOAD_PRG[i];

      if (x)
	{
	  CH_GetBuf(CH_TRK_FLASH_ON,&auto_buf );
	  DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
	  status = DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
	  LU_EXIT_IFERROR(status); 
	  status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,DAQ_STORE_MM,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
	  LU_EXIT_IFERROR(status);
	  status = RM_TaskSuspendUnlessSINT(100);
	  LU_EXIT_IFERROR(status);

	  DAQ_Format_CMD_Empty(&TRK_TempPif0);
	  CH_GetBuf(CH_TRK_RESET_FLASH,&auto_buf );
	  DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
	  
	  for (j=0; j < 6; j++)
	    {
	      if (PRH_TAB_TRK_DSP_OK[i][j])
		{
		  CH_GetBuf(TRK_PROG_ADR_BASE_ID+x-1,&auto_buf);
		  DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
		  {
		    DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
		    status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,DAQ_STORE_MM,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
		    LU_EXIT_IFERROR(status);
		    DAQ_Format_CMD_Empty(&TRK_TempPif0);
		  }
		  CH_GetBuf(TRK_LOAD_DATA_BASE_ID+j,&auto_buf);
		  DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
		}
	    }
	  
	  CH_GetBuf(CH_TRK_FLASH_OFF,&auto_buf );
	  DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
	  
	  DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
	  status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,DAQ_STORE_MM,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
	  LU_EXIT_IFERROR(status);	  		  
	}
      else
	{
	  for (j=0; j < 6; j++)
	    {
	      if (PRH_TAB_TRK_DSP_OK[i][j])
		{
		  DAQ_Format_CMD_Empty(&TRK_TempPif0);
		  DAQ_Format_CMD_Empty(&TRK_TempPif1);		  
		  CH_GetBuf(TRK_HEADER_PRG_BASE_ID+j,&auto_buf);
		  DAQ_Format_AppendBuffer(&TRK_TempPif1,auto_buf);

		  DAQ_Format_AppendBuffer(&TRK_TempPif1,&TRK_PROGRAM);

		  DAQ_Format_AppendBuffer(&TRK_TempPif1,&TRK_TRAILER_PRG[j]);
		  TRK_TempPif1.ato = TRK_TRAILER_PRG[j].ato;
		  TRK_TempPif1.eto = TRK_TRAILER_PRG[j].eto;
		  DAQ_Format_Fe2Daq(&TRK_TempPif0,&TRK_TempPif1,idaqfe);

		  DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);
		  status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,DAQ_STORE_MM,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
		  LU_EXIT_IFERROR(status);	  		  
		}
	    }
	}
    }
  
  DAQ_Format_CMD_Empty(&TRK_TempPif0);
  
  for( i=0, idaqfe = DAQ_FE_TRK_1; idaqfe <= DAQ_FE_TRK_2; idaqfe++,i++)
    {
      for(j=0; j < 6; j++)
	{
	  CH_GetBuf(TRK_START_BASE_ID+j,&auto_buf );

	  if (PRH_TAB_TRK_DSP_OK[i][j])
	    DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
	}
    }  
  
  for( i=0, idaqfe = DAQ_FE_TRK_1; idaqfe <= DAQ_FE_TRK_2; idaqfe++,i++)
    {
      for(j=0; j < 6; j++)
	{
	  if (PRH_TAB_TRK_DSP_OK[i][j])
	    DAQ_Format_Fe2Daq(&TRK_TempPif0,&TRK_NUMBER_DSP[i+1][j],idaqfe);
	}
    }  
  
  DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
  status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,DAQ_STORE_MM,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
  LU_EXIT_IFERROR(status);	  		  

  if (!RM_Init_Before_Calib)
    {
      DAQ_Format_CMD_Empty(&TRK_TempPif0);

      CH_GetBuf(CH_TRK_FLASH_ON,&auto_buf );
      DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,DAQ_FE_TRK_1);

      CH_GetBuf(CH_TRK_FLASH_ON,&auto_buf );
      DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,DAQ_FE_TRK_2);
      
      DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
      status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,DAQ_STORE_MM,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
      LU_EXIT_IFERROR(status);	  		  
      status = RM_TaskSuspendUnlessSINT(100);
      LU_EXIT_IFERROR(status);
      
      DAQ_Format_CMD_Empty(&TRK_TempPif0);
      
      for(i=0, idaqfe = DAQ_FE_TRK_1; idaqfe <= DAQ_FE_TRK_2; idaqfe++,i++)
	{
	  CH_GetBuf(CH_TRK_RESET_FLASH,&auto_buf );
	  DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);

	  for(k=0; k < 3; k++)
	    for(j=0; j < 6; j++)
	      {
		if (PRH_TAB_TRK_DSP_OK[i][j])
		  {
		    CH_GetBuf(TRK_CALIB_ADR_BASE_ID+j*21+k*7+(PRH_VAR_TRK_CALIB_INIT-TRK_CALIB_ADR_BASE_OFFSET),&auto_buf );
		    DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe); 
		    {
		      DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
		      status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,DAQ_STORE_MM,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
		      LU_EXIT_IFERROR(status);
		      DAQ_Format_CMD_Empty(&TRK_TempPif0);
		    }		    
		    CH_GetBuf(TRK_LOAD_DATA_BASE_ID+j,&auto_buf );
		    DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
		  }
	      }
	  
	  CH_GetBuf(CH_TRK_FLASH_OFF,&auto_buf );
	  DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
	}
      
      DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
      status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,DAQ_STORE_MM,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
      LU_EXIT_IFERROR(status);	  		  
      TRK_calib_used = PRH_VAR_TRK_CALIB_INIT;
    }
  
  TRK_status = 0;

  return status;
}

status_code TRK_Assemble_ReadCalibrationCmd(DAQ_CMD_BUF* board1,DAQ_CMD_BUF* board2) 
{
  int j;
  DAQ_CMD_BUF* auto_buf;

  DAQ_Format_CMD_Empty(board1);
  DAQ_Format_CMD_Empty(board2);
  
  
  for(j=0; j < 6 ; j++)
    {
      if (PRH_TAB_TRK_DSP_OK[0][j])
	{
	  CH_GetBuf(TRK_READ_HEADER_BASE_ID+j,&auto_buf );
	  DAQ_Format_Fe2Daq(board1,auto_buf,DAQ_FE_TRK_1);
	  
	  CH_GetBuf(TRK_READ_LADDER1_BASE_ID+j,&auto_buf );
	  DAQ_Format_Fe2Daq(board1,auto_buf,DAQ_FE_TRK_1);

	  CH_GetBuf(TRK_READ_LADDER2_BASE_ID+j,&auto_buf );
	  DAQ_Format_Fe2Daq(board1,auto_buf,DAQ_FE_TRK_1);

	  CH_GetBuf(TRK_READ_LADDER3_BASE_ID+j,&auto_buf );
	  DAQ_Format_Fe2Daq(board1,auto_buf,DAQ_FE_TRK_1);
	}

      if (PRH_TAB_TRK_DSP_OK[1][j])
	{
	  CH_GetBuf(TRK_READ_HEADER_BASE_ID+j,&auto_buf );
	  DAQ_Format_Fe2Daq(board2,auto_buf,DAQ_FE_TRK_2);
	      
	  CH_GetBuf(TRK_READ_LADDER1_BASE_ID+j,&auto_buf );
	  DAQ_Format_Fe2Daq(board2,auto_buf,DAQ_FE_TRK_2);

	  CH_GetBuf(TRK_READ_LADDER2_BASE_ID+j,&auto_buf );
	  DAQ_Format_Fe2Daq(board2,auto_buf,DAQ_FE_TRK_2);

	  CH_GetBuf(TRK_READ_LADDER3_BASE_ID+j,&auto_buf );
	  DAQ_Format_Fe2Daq(board2,auto_buf,DAQ_FE_TRK_2);
	}
    }

  return CM_RC_SUCCESSFUL;
}

status_code TRK_Send_ReadCalibrationCmd(SM_PAGEID page1,SM_PAGEID page2,
					DAQ_CMD_BUF* board1,DAQ_CMD_BUF* board2,
					DAQ_CMD_BUF* ans1,DAQ_CMD_BUF* ans2) 
{

  status_code status;
  PM_pi_SetPktType(HB_PKTTYPE_CALIB_TRK_1);
  DAQ_StoreCmdQueue2PIF(page1,board1);
  status = DAQ_SendCmd2PIFWaitDAQReply(page1,TRUE,ans1,ans1==NULL ? DAQ_NO_STORE_RAM : DAQ_STORE_RAM);
  LU_EXIT_IFERROR(status);
  
  PM_pi_SetPktType(HB_PKTTYPE_CALIB_TRK_2);
  DAQ_StoreCmdQueue2PIF(page2,board2);	    
  status = DAQ_SendCmd2PIFWaitDAQReply(page2,TRUE,ans2,ans2==NULL ? DAQ_NO_STORE_RAM : DAQ_STORE_RAM); 
  LU_EXIT_IFERROR(status);	 

  return CM_RC_SUCCESSFUL;
}


status_code TRK_Calibration(UINT32 trk_calib_mode)
{
  status_code status=CM_RC_SUCCESSFUL,s1,s2;
  UINT32 TRK_loop_calib,TRK_calib=trk_calib_mode;
  int i,j,k,n;
  DAQ_FE idaqfe;
  DAQ_CMD_BUF* auto_buf;
  UINT16 alarm_reg;
  BOOL redo_calib;

  TRK_status = 2; 
  TRK_loop_calib=0;
  // TRK_calib = PRH_VAR_TRK_CALIB_MODE;
  
  
  DAQ_ResetPIF(DAQ_DEFAULT_ETO_TICS,DAQ_MAX_DTO_TICS,SM_DAQSETUP,HB_PKTTYPE_CALIB_TRK_BOTH);

  //TBD set pif 128K
  //TBD set trigger in calib mode 

  do {
    redo_calib = FALSE;
  
    DAQ_Format_CMD_Empty(&TRK_TempPif0);
    PM_pi_SetPktType(HB_PKTTYPE_CALIB_TRK_BOTH);

    for(i=0, idaqfe = DAQ_FE_TRK_1; idaqfe <= DAQ_FE_TRK_2; idaqfe++,i++)
      {
	CH_GetBuf(CH_TRK_GENERAL_RESET,&auto_buf );
      DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
      
      for(j=0; j <6; j++)
	{
	  if (PRH_TAB_TRK_DSP_OK[i][j])
	    {
	      CH_GetBuf(TRK_START_BASE_ID+j,&auto_buf );
	      DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
	      DAQ_Format_Fe2Daq(&TRK_TempPif0,&TRK_NUMBER_DSP[i+1][j],idaqfe);
	    }
	}
      }
    
    DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
    
    status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,FALSE,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
    LU_EXIT_IFERROR(status); 
    TRK_calib_used = TRK_calib;
  
    if (TRK_calib > 100)
      {
	DAQ_Format_CMD_Empty(&TRK_TempPif0);
     
	for(i=0, idaqfe = DAQ_FE_TRK_1; idaqfe <= DAQ_FE_TRK_2; idaqfe++,i++)
	  {

	    CH_GetBuf(CH_TRK_READ_CR,&auto_buf);
	    DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);

	    TRK_ALARM_MASK[i]|=0xc0;
	    CH_GetBuf(TRK_MASK_BASE_ID+TRK_ALARM_MASK[i]-TRK_MASK_BASE_OFFSET,&auto_buf );

	    DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
	    CH_GetBuf(CH_TRK_FLASH_ON,&auto_buf );
	    DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
	  }
      
	DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    

	status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,FALSE,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
	LU_EXIT_IFERROR(status); 
      
	status = RM_TaskSuspendUnlessSINT(100);
	LU_EXIT_IFERROR(status);

	DAQ_Format_CMD_Empty(&TRK_TempPif0);
      
	for(i=0, idaqfe = DAQ_FE_TRK_1; idaqfe <= DAQ_FE_TRK_2; idaqfe++,i++)
	  {
	    CH_GetBuf(CH_TRK_RESET_FLASH,&auto_buf );
	    DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
	  
	    for(k=0; k < 3; k++)
	      for(j=0; j < 6; j++)
		{
		  if (PRH_TAB_TRK_DSP_OK[i][j])
		    {
		      CH_GetBuf(TRK_CALIB_ADR_BASE_ID+j*21+k*7+(PRH_VAR_TRK_CALIB_INIT-TRK_CALIB_ADR_BASE_OFFSET),&auto_buf );
		      DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
		      {
			DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
			status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,FALSE,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
			LU_EXIT_IFERROR(status);
			DAQ_Format_CMD_Empty(&TRK_TempPif0);
		      }
		      CH_GetBuf(TRK_LOAD_DATA_BASE_ID+j,&auto_buf );
		      DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
		    }
		}

	    CH_GetBuf(CH_TRK_FLASH_OFF,&auto_buf );
	    DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
	  }
      
	DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
	status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,FALSE,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
	LU_EXIT_IFERROR(status); 

	/*
	status=TRK_Assemble_ReadCalibrationCmd(&TRK_TempPif2,&TRK_TempPif3);
	LU_EXIT_IFERROR(status);
	status=TRK_Send_ReadCalibrationCmd(SM_CALEXP2,SM_CALEXP3,
					   &TRK_TempPif2,&TRK_TempPif3,
					   NULL,NULL);
	LU_EXIT_IFERROR(status);
	*/
      }
    else
      {
	DAQ_Format_CMD_Empty(&TRK_TempPif0);
	DAQ_Format_CMD_Empty(&TRK_TempPif1);
	DAQ_Format_CMD_Empty(&TRK_TempPif2);
	DAQ_Format_CMD_Empty(&TRK_TempPif3);

	for(i=0, idaqfe = DAQ_FE_TRK_1; idaqfe <= DAQ_FE_TRK_2; idaqfe++,i++)
	  {
	    TRK_ALARM_MASK[i]|=0xc0;
	    if(PRH_VAR_TB_LINK == 1 /* HOT */) 
	      TRK_ALARM_MASK[i] &= 0xBF;
	    else
	      TRK_ALARM_MASK[i] &= 0x7F;

	    CH_GetBuf(TRK_MASK_BASE_ID-TRK_MASK_BASE_OFFSET+TRK_ALARM_MASK[i],&auto_buf );
	    DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
	  
	    for(j=0; j < 6 ; j++)
	      {
		if (PRH_TAB_TRK_DSP_OK[i][j])
		  if (TRK_calib == 1)
		    {
		      CH_GetBuf(TRK_SET_CALIB_NORMAL_BASE_ID+j,&auto_buf );
		      DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
		    }
		  else
		    if (TRK_calib == 2)
		      {
			CH_GetBuf(TRK_SET_CALIB_SPECIAL_BASE_ID+j,&auto_buf );
			DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
			CH_GetBuf(TRK_EVENT_ACQ_BASE_ID+j,&auto_buf );
			DAQ_Format_Fe2Daq(&TRK_TempPif1,auto_buf,idaqfe);
			status = DAQ_StoreCmdQueue2PIF(SM_CALEXP1,&TRK_TempPif1);	    
			LU_EXIT_IFERROR(status);
		      }
	      }
	  }
      
	DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
	status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,FALSE,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
	LU_EXIT_IFERROR(status); 
            
	DAQ_Format_CMD_Empty(&TRK_TempPif0);
	CH_GetBuf(CH_TB_GIVE_ME_TRIGGER,&auto_buf );
	DAQ_Format_Cmd2Fe(&TRK_TempPif0,auto_buf,DAQ_SELECT_TRIG(PRH_VAR_TB_LINK)); 
	DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);
	if (TRK_calib == 2)
	  {
	    PM_pi_SetPktType(HB_PKTTYPE_EVENT_TRK);

	    for(k=0; k < PRH_VAR_TRK_NLOOP; k++) 
	      {
		for(n=0; n < 128; n++)
		  {
		    status = DAQ_SendCmdQueue2CMDIF(SM_CALEXP0);
		    LU_EXIT_IFERROR(status);
		    status = RM_TaskSuspendUnlessSINT(PRH_VAR_TRK_TIME_SHORT);
		    LU_EXIT_IFERROR(status);

		    status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP1,DAQ_STORE_MM,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
		    LU_EXIT_IFERROR(status);
		  }
		status = RM_TaskSuspendUnlessSINT(PRH_VAR_TRK_TIME_LONG);
		LU_EXIT_IFERROR(status);

	      }
	  }
	else 
	  if (TRK_calib == 1)
	    {
	      for(k=0; k < PRH_VAR_TRK_NLOOP; k++) 
		{
		  for(n=0; n < 128; n++)
		    {
		      status = DAQ_SendCmdQueue2CMDIF(SM_CALEXP0);
		      LU_EXIT_IFERROR(status); 
		      status = RM_TaskSuspendUnlessSINT(PRH_VAR_TRK_TIME_SHORT);
		      LU_EXIT_IFERROR(status);
		    }
		  status = RM_TaskSuspendUnlessSINT(PRH_VAR_TRK_TIME_LONG);
		  LU_EXIT_IFERROR(status);

		}
	    }

	PM_pi_SetExpPktCpyFlag(TRUE);

	status=TRK_Assemble_ReadCalibrationCmd(&TRK_TempPif2,&TRK_TempPif3);
	LU_EXIT_IFERROR(status);

	status=TRK_Send_ReadCalibrationCmd(SM_CALEXP2,SM_CALEXP3,
					   &TRK_TempPif2,&TRK_TempPif3,
					   &TRK_daq_reply0,&TRK_daq_reply1);
	LU_EXIT_IFERROR(status);
      

	PM_pi_SetExpPktCpyFlag(FALSE);

	if (TRK_calib == 2)
	  {
#warning To set in EEPROM TRK_CALIB_MODE
	    PRH_VAR_TRK_CALIB_MODE=TRK_calib = 1;
	  }     
	s1 = TRK_CheckPacket(&TRK_daq_reply0,DAQ_FE_TRK_1);
      
	s2 = TRK_CheckPacket(&TRK_daq_reply1,DAQ_FE_TRK_2);

	if (s1 != CM_RC_SUCCESSFUL || s2 != CM_RC_SUCCESSFUL )   // everything is ok    
	  {
	    if (TRK_loop_calib >=3) 
	      TRK_calib = PRH_VAR_TRK_CALIB_INIT;
	    TRK_loop_calib++;
	    redo_calib = TRUE;
	  }
      }
  }while(redo_calib);
    
  TRK_status = 0;

  return status;
}

#if 0
status_code TRK_Alarm()
{
  int alarm_link=0,j,i;
  DAQ_FE idaqfe;
  status_code status;
  DAQ_CMD_BUF* auto_buf;

  // TDB read KHB alarm register
  DAQ_Format_CMD_Empty(&TRK_TempPif0);

  CH_GetBuf(CH_TRK_READ_CR,&auto_buf );
  DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,DAQ_FE_TRK_1+alarm_link);

  DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
  status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,FALSE,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
  LU_EXIT_IFERROR(status);	  
  
  // TBD write in HK reply 

  DAQ_Format_CMD_Empty(&TRK_TempPif0);
  CH_GetBuf(CH_TRK_GENERAL_RESET,&auto_buf );
  DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,DAQ_FE_TRK_1+alarm_link);

  CH_GetBuf(CH_TRK_READ_CR,&auto_buf );

  DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,DAQ_FE_TRK_1+alarm_link);
  DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
  status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,FALSE,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
  LU_EXIT_IFERROR(status);	  

  // TBD unmasked alarm ?

  switch(TRK_status)
    {
    case 1:
      break;
    case 2:
      break;
    default:
      //TDB if (DS)
      if (1)
	{
	  DAQ_Format_CMD_Empty(&TRK_TempPif0);
	  for(i=0, idaqfe = DAQ_FE_TRK_1; idaqfe <= DAQ_FE_TRK_2; idaqfe++,i++)
	    {
	      for(j=0; j < 6 ; j++)
		{
		  CH_GetBuf(TRK_READ_HEADER_BASE_ID+j,&auto_buf );

		  if (PRH_TAB_TRK_DSP_OK[i][j])
		    DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);
		}
	    }
	  
	  DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
	  status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,FALSE,&TRK_daq_reply0,DAQ_NO_STORE_RAM);
	  LU_EXIT_IFERROR(status);	  

	}
      else
	{
	  TRK_status = 0;
	  TRK_Reset();
	}
    }
  

  return CM_RC_SUCCESSFUL;
}
#endif 

status_code TRK_Error_Handler()
{
  status_code status=CM_RC_SUCCESSFUL;
  DAQ_FE idaqfe;
  DAQ_CMD_BUF* auto_buf,*daq_reply;
  BYTE do_check;
  UINT16 status_reg;


  do_check = 0;

  for(idaqfe = DAQ_FE_TRK_1; idaqfe <= DAQ_FE_TRK_2 ; idaqfe++)
    {

      CH_GetBuf(CH_TRK_READ_CR,&auto_buf);
      DAQ_Format_CMD_Empty(&TRK_TempPif0);

      DAQ_Format_Fe2Daq(&TRK_TempPif0,auto_buf,idaqfe);

      status = DAQ_StoreCmdQueue2PIF(SM_CALEXP0,&TRK_TempPif0);	    
      if (status) 
	{
	  status = CM_RC_DO_RESET_IF_ALM;
	  return(status);
	}
      
      daq_reply = idaqfe==DAQ_FE_TRK_1 ? &TRK_daq_reply0 : &TRK_daq_reply1;
      status = DAQ_SendCmd2PIFWaitDAQReply(SM_CALEXP0,DAQ_STORE_MM,
					   daq_reply ,
					   DAQ_STORE_RAM);

      if (status || (daq_reply->len != SM_PKTHEADER_LEN+11 /* must be 27*/)) 
	{
	  status = CM_RC_DO_RESET_IF_ALM;
	  return(status);
	}
      
      // some check here
      
      do_check |= 
	(daq_reply->buf[SM_PKTHEADER_LEN+1] & (1<<7)) |
	daq_reply->buf[SM_PKTHEADER_LEN+2] |
	daq_reply->buf[SM_PKTHEADER_LEN+3] |
	daq_reply->buf[SM_PKTHEADER_LEN+4] ;
      
    }

  if (do_check)
    {
      status = HK_ReadKHBStatusRegister(&status_reg);
      if (status) 
	{
	  status = CM_RC_DO_RESET_IF_ALM;
	  return(status);
	}
      
      status_reg&=(KHB_STS_ALARM_IDAQ | KHB_STS_ALARM_TRK);

      if (status_reg == 0)
	{
	  
	      if (PRH_VAR_GOM_DURING_ALARM == MH_GOM_INITIALIZATION)
		status = CM_RC_DO_RESET_IF_ALM;
	      else
		if (PRH_VAR_GOM_DURING_ALARM == MH_GOM_CALIBRATION)
		  {
		    if (PRH_VAR_TRK_CALIB_MODE > 100)
		      status = CM_RC_DO_RESET_IF_ALM;
		    else
		      {
			// PRH_VAR_TRK_CALIB = PRH_VAR_TRK_CALIB_INIT;
			// TRK_Calib = PRH_VAR_TRK_CALIB_INIT;
			status = TRK_Calibration(PRH_VAR_TRK_CALIB_INIT);
			if (status)
			  status = CM_RC_DO_RESET_IF_ALM;
			else
			  {
			    status = HK_ReadKHBStatusRegister(&status_reg);
			    status_reg&=(KHB_STS_ALARM_IDAQ | KHB_STS_ALARM_TRK | KHB_STS_ALARM_TRG) & PRH_VAR_MASK_ACQ_ALARM;
			    
			    if (status || status_reg)
			      status = CM_RC_DO_RESET_IF_ALM;
			  }
		      }
		  }
		else
		  if (PRH_VAR_GOM_DURING_ALARM == MH_GOM_ACQUISITION)
		    {
		      if(
			 (TRK_daq_reply0.buf[SM_PKTHEADER_LEN+2] & 0x3F) |
			 (TRK_daq_reply1.buf[SM_PKTHEADER_LEN+2] & 0x3F) )
			status = CM_RC_DO_POWER_OFF_ON;
		      else
			status = CM_RC_DO_RESET_IF_ALM;
		    }
	}
      else
	status = CM_RC_DO_RESET_IF_ALM;
    }

  return status;
}

status_code TRK_ChkSensors(UINT16 command1,UINT16 command2,UINT16 expected,ALM_VAR_ID log_id,UINT16 pkttype_id)
{
  UINT16 combuf;
  UINT16 outbuf[TRK_TSB_MAX_REPLY];
  int i;
  BYTE board;
  status_code status=CM_RC_SUCCESSFUL,offst;

  if((PRH_ARR_TSB_BOARD_OK[0] | PRH_ARR_TSB_BOARD_OK[1]) == 0)
     return CM_RC_SUCCESSFUL;

#if 0
  status = PWR_CMD2PSB(PRH_ARR_PSB_COMMANDS[PWR_PSB_TRACKER_SENSOR_ON],TM_PSB_ALARM,CM_OFF,
		       log_id,log_id+1,PWR_PSB_STANDARD_ANSWER);
#endif

  for(board=0;board<2;board++) 
    {
      if(PRH_ARR_TSB_BOARD_OK[board]) {
	combuf = board==0 ? command1 : command2;
	status = HK_KHB_Cmd2FE(board==0 ? KHB_TRACKER_SENSORS_1 : KHB_TRACKER_SENSORS_2  ,
			       1,expected,&combuf,outbuf,TRK_TSB_TIMEOUT);
	
	DAQ_BUFFER_EMPTY(TRK_tempbuf);
	DAQ_WRITE_BE_UINT8(TRK_tempbuf,status);
	switch(status)
	  {
	  case CM_RC_KHB_ERROR:
	    /*@LOG TRK_ChkSensors: TSB0 , KHB Error */
	    ALM_WriteLog(ALM_TRACE_ID,log_id+2); 
	    status = CM_RC_SUCCESSFUL;
	    break;
	  case CM_RC_TIMEOUT:
	    /*@LOG TRK_ChkSensors: TSB0 , reading Timeout */
	    ALM_WriteLog(ALM_TRACE_ID,log_id+3);
	    for(i=0; i < expected; i++)
	      if(i<outbuf[0])
		 DAQ_WRITE_BE_UINT16(TRK_tempbuf,outbuf[i+1]);
	      else
		 DAQ_WRITE_BE_UINT16(TRK_tempbuf,0xFFFF);
	    TRK_WriteInLog(pkttype_id,&TRK_tempbuf);
	    status = CM_RC_SUCCESSFUL;
	    break;
	  case CM_RC_SUCCESSFUL:
	    for(i=0; i < expected; i++)
	      DAQ_WRITE_BE_UINT16(TRK_tempbuf,outbuf[i]);
	    TRK_WriteInLog(pkttype_id,&TRK_tempbuf);
	    break;
	  default:
	    /*@LOG TRK_ChkSensors: unrecognized error board 0 - status */
	    LU_INFN_LOG(LU_CRITICAL|LU_HA,LU_MASK(__FILEID__),__FILEID__,__LINE__,status);
	  }
      }
      
    }
    
#if 0
  offst = PWR_CMD2PSB(PRH_ARR_PSB_COMMANDS[PWR_PSB_TRACKER_SENSOR_OFF],TM_PSB_ALARM,CM_OFF,
		      log_id+6,log_id+7,PWR_PSB_STANDARD_ANSWER);
  
  if (offst) {
    /*@LOG TRK_ChkSensors: TSB OFF, error */
    ALM_WriteLog(ALM_TRACE_ID,log_id); 
    status = CM_RC_DO_POWER_OFF_ON;
  }
#endif
  return CM_RC_SUCCESSFUL;
}

status_code TRK_CheckBSensors()
{
  return TRK_ChkSensors(TRK_TSB0_READ_B,TRK_TSB1_READ_B,7,ALM_TRK_TSB_ID_8,HB_PKTTYPE_TSB_B);
}

status_code TRK_CheckTSensors()
{
  return(TRK_ChkSensors(TRK_TSB0_READ_T,TRK_TSB1_READ_T,13,ALM_TRK_TSB_ID_0,HB_PKTTYPE_TSB_T));
}

status_code TRK_WriteInLog(BYTE pkttype,DAQ_CMD_BUF *b)
{
  status_code s;
  switch(pkttype) {
  case HB_PKTTYPE_TSB_T:
    s=HB_StoreTSB_T(b);
    break;
  case HB_PKTTYPE_TSB_B:
    s=HB_StoreTSB_B(b);
    break;
  default:
    /*@LOG pkttype error in TRK_WriteInLog - pkttype */
    LU_INFN_LOG(LU_INTERNAL|LU_HA,LU_MASK(__FILEID__),__FILEID__,__LINE__,pkttype);
  }
  return s;
}
