
(* Activate all xbots *)
FUNCTION_BLOCK PMC_ActivateXbots
	(*Determine whether to request an event ID*)
	requestEventID := TRUE;

	PMC_CmdProcessor(Execute, 0,requestEventID, PM_Controller, PMCFuncInfo, Ack,Done, Busy, Error, ErrorID, Aborted);

	IF PMCFuncInfo.SendToPMC THEN
		CASE PMCFuncInfo.MsgPartNStatus OF
			1:  (* Statement section case 1            *)
				(*SendToPMCDataRegion//*)
				(*Sending Command to PMC*)
				(* read current heart beat of field bus*)
				memcpy(pDest := ADR(cmdHB),pSrc := PM_Controller.P2H_START + PM_Controller.PMC_Constants.P2H_CMDC_OFFSET,length := 1);
				(*update command heart beat*)
				cmdHB := cmdHB + 1;
				cmdHB := cmdHB AND 255;
				(*--------------write command info*)
				(*command ID*)
				memcpy(pDest := PM_Controller.H2P_START + PM_Controller.PMC_Constants.H2P_CMDID_OFFSET,pSrc := ADR(cmdID),length := 2);
				(*event ID*)
				memcpy(pDest := PM_Controller.H2P_START + PM_Controller.PMC_Constants.H2P_EVENTID_OFFSET,pSrc := ADR(PMCFuncInfo.EventID),length := 2);
				(*write command heart beat*)
				memcpy(pDest := PM_Controller.H2P_START + PM_Controller.PMC_Constants.H2P_CMDC_OFFSET,pSrc := ADR(cmdHB),length := 1);
				(*SendToPMCDataRegionEnd//*)
				PMCFuncInfo.MsgPartNStatus := 0;   (*finished sending, report all done*)
			ELSE  (* Statement section ELSE*)
				PMCFuncInfo.MsgPartNStatus := -2;   (*error detected, invalid part*)
		END_CASE;
	END_IF;

	IF PMCFuncInfo.ReadFromPMC THEN
		CASE PMCFuncInfo.MsgPartNStatus OF
			1:
				(*ReadFromPMCDataRegion//*)
			
				(*ReadFromPMCDataRegionEnd//*)
				PMCFuncInfo.MsgPartNStatus := 0;  (*finished sending, report all done*)
			ELSE
				PMCFuncInfo.MsgPartNStatus := -2;   (*wrong part number*)
		END_CASE;
	END_IF;

	IF PMCFuncInfo.SendToPMC OR PMCFuncInfo.ReadFromPMC THEN
		PMC_CmdProcessor(Execute, 1,requestEventID, PM_Controller, PMCFuncInfo, Ack,Done, Busy, Error, ErrorID, Aborted);
	END_IF;

	(*timeout check, overrides the cmdprocessor outputs in case it has implementation errors. Hard timeout check*)
	IF Execute = TRUE AND Busy = TRUE THEN
		timeout := timeout + 1;
		IF timeout > PM_Controller.PMC_Constants.PMC_TIMEOUT THEN
			ErrorID := 8201;    (*timeout error id*)
			Error := TRUE;
			Busy := FALSE;
			Aborted := FALSE;
			Ack := FALSE;
			Done := FALSE;
			(*reset the event ID *)
			IF PMCFuncInfo.EventID <> 0 THEN
				PM_Controller.EventMgmt.ExecutingEventID[PMCFuncInfo.EventID] := FALSE;
				PMCFuncInfo.EventID := 0;
			END_IF;  
			(*the command processor will close the ticket,*)
			PMCFuncInfo.CmdSta := 30; (*idle state, and not change any outputs such as ErrorID or Eroor*)
			PMC_CmdProcessor(Execute, 2,requestEventID, PM_Controller, PMCFuncInfo, Ack,Done, Busy, Error, ErrorID, Aborted);
		END_IF;
	ELSE
		timeout := 0;
	END_IF;

	(*if eventID was not requested, then Done shares its value with Ack*)
	IF NOT(requestEventID) THEN
		Done := Ack;
	END_IF;
END_FUNCTION_BLOCK
