///////////////////////////////////////////////////////////////////////////////
//                                                                           //
// Copyright (c) 2000-2019 Ericsson Telecom AB                               //
//                                                                           //
// All rights reserved. This program and the accompanying materials          //
// are made available under the terms of the Eclipse Public License v2.0     //
// which accompanies this distribution, and is available at                  //
// https://www.eclipse.org/org/documents/epl-2.0/EPL-2.0.html                                 //
///////////////////////////////////////////////////////////////////////////////

///////////////////////////////////////////////////////////
//  Module: EPTF_CLL_Base_Functions
// 
//  Purpose:
//    This module contains the implementation of generic EPTF_CLL_Base functions.
// 
//  Module depends on:
//    <EPTF_CLL_Base_Definitions>
//    <EPTF_CLL_Commmon_Functions>
// 
//  Current Owner:
//    Jozsef Gyurusi (ETHJGI)
// 
//  Last Review Date:
//    2009-05-14
//
//  Detailed Comments:
//    This module contains the interface functions for the EPTF_CLL_Base.
//    Public functions:
//      <f_EPTF_Base_init_CT>
//      <f_EPTF_Base_registerCleanup>
//      <f_EPTF_Base_cleanup_CT>
//      <f_EPTF_Base_stop>
//      <f_EPTF_Base_stopRemote>
//      <f_EPTF_Base_stopAll>
//      <f_EPTF_Base_selfName>
//      <f_EPTF_Base_cleanupIsInProgress>
//      <f_EPTF_Base_wait4Shutdown>
//      <f_EPTF_Base_waitForCondition>
//      <f_EPTF_Base_upcast>
//      <f_EPTF_Base_downcast>
//      <f_EPTF_Base_getRelTimeInSecs>
//      <f_EPTF_Base_getRelTimeOffsetInSecs>
//      <f_EPTF_Base_getAbsTimeInSecs>
//      <f_EPTF_Base_getTimeOfDay>
//      <f_EPTF_Base_setNegativeTestMode>
//      <f_EPTF_Base_getNegativeTestMode>
//      <f_EPTF_Base_assert>
//      <f_EPTF_Base_nofAssertMsgs>
//      <f_EPTF_Base_getAssertMsg>
//      <f_EPTF_Base_setExpectedAssertMsg>
//      <f_EPTF_Base_setExpectedErrorMsg>
//      <f_EPTF_Base_checkExpectedAssert>
//      <f_EPTF_Base_checkExpectedError>
//      <f_EPTF_Base_getPid>
//      <f_EPTF_Base_getHostName>
//      <f_EPTF_Base_getComponentInfoByName>
//      <f_EPTF_Base_getPidByName>
//      <f_EPTF_Base_getComponentInfoAll>
//      <f_EPTF_Base_setDTEHandling>
//      <f_EPTF_Base_isEnabledDTEHandling>
//      <f_EPTF_Base_system>
//      <f_EPTF_Base_executeShell>
//      <f_EPTF_Base_getStartCommand>
//      <f_EPTF_Base_restart>
//
///////////////////////////////////////////////////////////////

module EPTF_CLL_Base_Functions {

import from EPTF_CLL_Base_Definitions all;
import from EPTF_CLL_Common_Functions all;
import from EPTF_CLL_Common_Definitions all;


///////////////////////////////////////////////////////////
// _Group: Public
//
// Purpose:
//   Public functions. Only these functions can be used by the user of <EPTF_Base_CT>
//
// Elements:
///////////////////////////////////////////////////////////
group Public {

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_init_CT
// 
//  Purpose:
//    Initialises the EPTF_Base_CT component
//
//  Parameters:
//    -
//
//  Return Value:
//    -
//
//  Errors:
//    -
//
//  Detailed Comments:
//    This function should be called before using the EPTF Base
//    component.
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_init_CT(in charstring pl_selfName) runs on EPTF_Base_CT_private {
  if (v_EPTF_Base_initialized) {
    return;
  }
  v_selfName := pl_selfName;
  v_EPTF_Base_cleanupFunctions := {};
  v_EPTF_Base_componentsToStop := {};
  v_EPTF_Base_componentInfoList := {};
  v_EPTF_Base_getCompInfoResult := {};
  f_EPTF_Base_addComponentInfo(f_EPTF_Base_downcast(f_EPTF_Base_upcast(self)),v_selfName,f_EPTF_Base_getHostName(),f_EPTF_Base_getPid());
  v_EPTF_Base_disableBye := false;
  v_EPTF_Base_byeAckReceived := false;
  v_EPTF_Base_stopRemoteSentTo := null;
  v_EPTF_Base_negativeTestMode := false;
  v_EPTF_Base_assertMsgs := {};
  v_EPTF_Base_expectedAssert := "";
  v_EPTF_Base_expectedError := "";
  v_EPTF_Base_enableDTEHandling := tsp_EPTF_Base_enableDTEHandling;
  // notify mtc:
  if (self != mtc) {
    connect(self:EPTF_Base_MgmtIf,mtc:EPTF_Base_MgmtIf); // mtc will close the connection
    f_EPTF_Base_send({hello := {f_EPTF_Base_getPid(),v_selfName,f_EPTF_Base_getHostName()}},mtc);
    //disconnect(self:EPTF_Base_MgmtIf,mtc:EPTF_Base_MgmtIf);
  }
  T_EPTF_componentClock.start;
  v_EPTF_Base_abstimeOfZeroComponentClock := f_EPTF_Base_getTimeOfDay();
  v_EPTF_Base_def := activate(as_handle_main_EPTF_Base_MgmtIf());
  v_EPTF_Base_initialized := true;

  f_EPTF_Base_registerCleanup(refers(f_EPTF_Base_cleanup_CT));
  if (tsp_EPTF_Base_debug){
    f_EPTF_Common_user(log2str("----BASE INIT DONE FOR COMPONENT ",v_selfName,"----"));
  }
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_registerCleanup
// 
//  Purpose:
//    This function should be called at the end of the init function of any component that extends EPTF_Base_CT component (explicitly or implicitly)
//
//  Parameters:
//    pl_featureCleanupFn - *in* <f_EPTF_Feature_cleanup_CT> - the cleanup function that should be called before terminating the user component
//
//  Return Value:
//    -
//
//  Errors:
//    -
//
//  Detailed Comments:
//    This function should be called in a component that extends (explicitly or implicitly) the EPTF_Base_CT
//    with the argument of the cleanup function of the given component ('self.cleanup')
//    The cleanup function itself should not call f_EPTF_Base_cleanup_CT.
//    But if you call f_EPTF_Base_cleanup_CT inside your cleanup function put it after
//    the line where you have set the v_initialized flag to false, otherwise, if your cleanup function was registered,
//    it will be called twice!
//
//    The registered cleanup function should make sure, that all components that were created by the
//    current component (=feature) will be stopped. Also all open port connections belonging
//    to the current component should be closed and the connected component should be notified
//    about the termination of the connection.
//
//    Note, that before the component exits, either <f_EPTF_Base_stop>, <f_EPTF_Base_cleanup_CT> or <f_EPTF_Base_stopAll> has to be called!
//
//    So the best rule:
//     - in your init function call all the init functions of those components that your component extends explicitly
//     - after that, initialize your component variables
//     - activate your main event handler altstep as default before the init function calls if you would like to set
//       the lowest priority for it, or after the init function calls for the highest priority.
//       Always use the lowest priority for your altstep! Otherwise your altstep can affect the priorities in EPTF.
//       Note, that the order of the init function calls may affect the default altstep priorities.
//       The altstep for the latter init function normally will get higher priority unless 
//       the earlier component extends the latter component and sets highest priority for itself.
//     - register your cleanup function by f_EPTF_Base_registerCleanup at the end of your init function
//     - do not call any cleanup function inside your cleanup function
//     - call f_EPTF_Base_cleanup_CT before your component terminates
//       or call f_EPTF_Base_stop if the execution should be stopped by an error (forced to stop immediately)
//     - Make sure, that your init and cleanup functions can be called several times (with doing nothing during the additional calls)!
//     - Make sure, that after your cleanup function is called, your component can be terminated without leaving
//       any pending operations in the target system (or in other EPTF components),
//       and that all other PTC-s that should be alive can continue operation without error.
//
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_registerCleanup(in f_EPTF_Feature_cleanup_CT pl_featureCleanupFn) runs on EPTF_Base_CT_private {
  if (v_EPTF_Base_initialized == false) {
    f_EPTF_Common_error(log2str("ERROR:","f_EPTF_Base_init_CT is not called before calling f_EPTF_Base_registerCleanup for ", pl_featureCleanupFn));
    
  }
  for (var integer i:=0; i<sizeof(v_EPTF_Base_cleanupFunctions); i:=i+1) {
    if (pl_featureCleanupFn == v_EPTF_Base_cleanupFunctions[i]) {
      // already registered
      return;
    }
  }
  v_EPTF_Base_cleanupFunctions[sizeof(v_EPTF_Base_cleanupFunctions)] := pl_featureCleanupFn;
}


///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_cleanup_CT
// 
//  Purpose:
//    This function should be called on any component that extends the EPTF_Base_CT as the last function call
//    before the component terminates to shut the component down gracefully.
//
//  Parameters:
//    -
//
//  Return Value:
//    -
//
//  Errors:
//    -
//
//  Detailed Comments:
//    This function makes it possible to be able to shut down the component that extends <EPTF_Base_CT> gracefully.
//    It calls all registered cleanup functions backwards as they were registered.
//
//    This function can be called inside or outside the main alt-loop. The main alt-loop
//    will terminate if there is no 'repeat' statement after calling f_EPTF_Base_cleanup_CT.
//    This is because f_EPTF_Base_cleanup_CT does not terminate the component.
//    The stop; statement can only be called after f_EPTF_Base_cleanup_CT returned.
//    To terminate the component use the function <f_EPTF_Base_stop> instead.
//    The f_EPTF_Base_cleanup_CT function can normally be used as the last function call in the
//    component's behaviour function (a function that is started on the component). On all other
//    places use <f_EPTF_Base_stop>.
//
//    Note, that f_EPTF_Base_cleanup_CT is a blocking function. This means that the execution blocked until
//    all cleanup function finished its operation.
//    
///////////////////////////////////////////////////////////
public function f_EPTF_Base_cleanup_CT() runs on EPTF_Base_CT_private {
  if (v_EPTF_Base_initialized == false) {
    return;
  }
  v_EPTF_Base_initialized := false;
  // the flag should be set before the for cycle, otherwise the
  // cycle would be executed more than once, if a cleanup function called f_EPTF_Base_cleanup_CT
  if (tsp_EPTF_Base_debug){
    f_EPTF_Common_user("----BASE CLEANUP START----");
  }
  if (mtc == self) {
    f_EPTF_Base_stopAllComponents();
  }

  // should go backwards! :
  for (var integer i:=sizeof(v_EPTF_Base_cleanupFunctions)-1; i>-1; i:=i-1) {
    if (tsp_EPTF_Base_debug){
        f_EPTF_Common_user(log2str("DEBUG:","Calling cleanup function ",v_EPTF_Base_cleanupFunctions[i]));
    }
    v_EPTF_Base_cleanupFunctions[i].apply();
    if (tsp_EPTF_Base_debug){
        f_EPTF_Common_user(log2str("DEBUG:","Cleanup function done ",v_EPTF_Base_cleanupFunctions[i]));
    }
  }
  
  if (v_EPTF_Base_expectedAssert!="") { // only check if it was specified
    if (f_EPTF_Base_checkExpectedAssert(v_EPTF_Base_expectedAssert)) {
      setverdict(pass);
    } else {
      setverdict(fail, "Expected assert:", v_EPTF_Base_expectedAssert, " missing");
    }
  }
  if (v_EPTF_Base_expectedError!="") { // only check if it was specified
    if (f_EPTF_Base_checkExpectedError(v_EPTF_Base_expectedError)) {
      setverdict(pass);
    } else {
      setverdict(fail, "Expected error:", v_EPTF_Base_expectedError, " missing");
    }
  }

  // if I am the mtc check if all components have exited:
  if (mtc == self) {
    f_EPTF_Base_stopAllComponents();
//    var EPTF_Base_MgmtMsg vl_EPTF_Base_MgmtIf_msg;
//    var EPTF_Base_CT vl_EPTF_Base_MgmtIf_msg_sender;
    timer t_periodicStop := 2.0;
    t_periodicStop.start;
    alt {
      [] all component.done;
      [] t_periodicStop.timeout {
        f_EPTF_Base_stopAllComponents();
        t_periodicStop.start;
        repeat;
      }
    }
    //setverdict(none);
  } else {
    // do not send bye to MTC if MTC wants me to stop:
    if (v_EPTF_Base_disableBye == false) {
      //connect(self:EPTF_Base_MgmtIf,mtc:EPTF_Base_MgmtIf); // connection will be closed when byeAck received
      f_EPTF_Base_send({bye := {}},mtc);
      f_EPTF_Base_waitForByeAck();
      disconnect(self:EPTF_Base_MgmtIf,mtc:EPTF_Base_MgmtIf); // Permanent connection will be closed here
    }
  }

  if(T_EPTF_componentClock.running) { T_EPTF_componentClock.stop; }

  v_EPTF_Base_stopRemoteSentTo := null;
  if (tsp_EPTF_Base_debug){
    f_EPTF_Common_user(log2str("----BASE CLEANUP DONE FOR ",v_selfName,"----"));
  }
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_stop
// 
//  Purpose:
//    This function should be called to force the current component to terminate
//
//  Parameters:
//    pl_verdict - *in verdicttype* - the verdict to set (default: fail) (FIXME: to be changed to none)
//
//  Return Value:
//    -
//
//  Errors:
//    -
//
//  Detailed Comments:
//   Wrapper around 'stop', but shuts down the component gracefully by calling the cleanup functions.
//   (To stop without cleanups use stop;)
//   All 'stop;' should be replaced with 'f_EPTF_Base_stop();'
//   The current component is terminated before the function returns. (blocking stop)
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_stop(in verdicttype pl_verdict := fail) runs on EPTF_Base_CT_private {
  if (pl_verdict != none and not v_EPTF_Base_negativeTestMode) {
    setverdict(pl_verdict);
  }
  if (v_EPTF_Base_initialized == false) {
    f_EPTF_Common_warning(log2str("Warning:","Stop requested during cleanup. Cleanup is aborted."));
    stop; // cleanup is in progress, additional stop forces component to stop without further cleanup!
  }
  if (tsp_EPTF_Base_debug){
    f_EPTF_Common_user("Trying to stop execution gracefully...");
  }
  f_EPTF_Base_cleanup_CT();
  stop;
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_stopRemote
// 
//  Purpose:
//    This function should be called to force any remote component that extends EPTF_Base_CT to terminate
//
//  Parameters:
//    pl_remoteComp - <EPTF_Base_CT> - the remote component to stop
//    pl_noCleanup - *boolean* - true if stops without cleanup (fast method), default: false
//
//  Return Value:
//    -
//
//  Errors:
//    -
//
//  Detailed Comments:
//   Shuts down the remote component gracefully. The current component continues its operation except it is called with mtc.
//
//   If called with pl_remoteComp := mtc, the whole system will be shut down. This is equivalent to f_EPTF_Base_stopAll(none);
//   In this case the function does not return. The current component is terminated inside this function call;
//
//   If called with pl_remoteComp := self, the component it is called on will be shut down. The difference between this and f_EPTF_Base_stop(none);
//   is that the latter will not return (component is terminated before the function returns) while the first will return and the termination of the component
//   will be started on a different alt level (at which the stopRemote event is handled) (non-blocking stop).
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_stopRemote(in EPTF_Base_CT_private pl_remoteComp, in boolean pl_noCleanup := false) runs on EPTF_Base_CT_private {
  if (tsp_EPTF_Base_debug){
    f_EPTF_Common_user(log2str("Requesting to stop execution of component ",pl_remoteComp," gracefully..."));
  }

  if (self == mtc) {
    // I want to stop somebody and I am the mtc: remote will be terminated, so it has to be removed from the database:
    f_EPTF_Base_removeComponent(pl_remoteComp);
  }
  
  if (pl_remoteComp == mtc) {
    if (v_EPTF_Base_initialized == false) {
      f_EPTF_Common_warning(log2str("Warning:","Cleanup is in progress, additional stopRemote is ignored for pl_remoteComp: mtc."));
      return; // do nothing: cleanup is in progress, additional stopRemote is ignored!
    }
    if (self != mtc) {
      //connect(self:EPTF_Base_MgmtIf,pl_remoteComp:EPTF_Base_MgmtIf);
      f_EPTF_Base_send({stopRemote := {pl_noCleanup}},pl_remoteComp);
      if (pl_noCleanup == true) { //Permanent connection has to be closed here
        disconnect(self:EPTF_Base_MgmtIf,pl_remoteComp:EPTF_Base_MgmtIf);
      }
      f_EPTF_Base_wait4Shutdown(); // StopRemote with wait4Shutdown
    }
//    else {   // StopRemote with wait4Shutdown
      if (pl_noCleanup == false) {
        v_EPTF_Base_disableBye := true;
        f_EPTF_Base_cleanup_CT();
      }
//  }        // StopRemote with wait4Shutdown
    stop;
  }
  // send stopRemote to remoteComp, which cannot be the mtc here
  connect(self:EPTF_Base_MgmtIf,pl_remoteComp:EPTF_Base_MgmtIf);
  f_EPTF_Base_send({stopRemote := {pl_noCleanup}},pl_remoteComp);
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_stopAll
// 
//  Purpose:
//    This function should be called to force all components that extends EPTF_Base_CT to terminate
//
//  Parameters:
//    pl_verdict - *in verdicttype* - the verdict to set (default: fail) (FIXME: to be changed to none)
//    pl_noCleanup - *in boolean* - true if stops without cleanup (fast method), default: false
//
//  Return Value:
//    -
//
//  Errors:
//    -
//
//  Detailed Comments:
//   Shuts down all components gracefully. The current component is terminated before the function returns. (blocking stop)
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_stopAll(in verdicttype pl_verdict := fail, in boolean pl_noCleanup := false) runs on EPTF_Base_CT_private {
  if (pl_verdict != none and not v_EPTF_Base_negativeTestMode) {
    setverdict(pl_verdict);
  }
  if (tsp_EPTF_Base_debug){
    f_EPTF_Common_user("Trying to stop execution of all components gracefully...");
  }
  f_EPTF_Base_stopRemote(mtc,pl_noCleanup);
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_selfName
// 
//  Purpose:
//    Returns the name of the component, that was specified in the <f_EPTF_Base_init_CT> function
//
//  Parameters:
//    -
//
//  Return Value:
//    charstring - the name of the component
//
//  Errors:
//    -
//
//  Detailed Comments:
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_selfName() runs on EPTF_Base_CT_private  return charstring {
  return v_selfName;
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_cleanupIsInProgress
// 
//  Purpose:
//    Returns true after the base cleanup function was called (when the function is entered)
//    and the cleanup mechanism is in progress or has finished.
//
//  Parameters:
//    -
//
//  Return Value:
//    charstring - the name of the component
//
//  Errors:
//    -
//
//  Detailed Comments:
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_cleanupIsInProgress() runs on EPTF_Base_CT_private  return boolean {
  return v_EPTF_Base_initialized;
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_wait4Shutdown
// 
//  Purpose:
//    Main event loop.
//
//  Parameters:
//    -
//
//  Return Value:
//    -
//
//  Errors:
//    -
//
//  Detailed Comments:
//    This function waits for the component clock timeout, i.e. it waits
//    indefinitely, but keeps the default altsteps of EPTF running.
//    Since the timeout is an alt statement, the wait for timeout is skipped
//    once a default altstep runs and don't `repeat' the alt snapshot.
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_wait4Shutdown() runs on EPTF_Base_CT_private
{
  T_EPTF_componentClock.timeout;
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_waitForCondition
// 
//  Purpose:
//    A general function to wait for a condition to become true.
//    It blocks the execution until the pl_checkCondFn function returns true.
//
//  Parameters:
//    pl_checkCondFn - in <EPTF_Base_CheckCondition_FT> - reference to the function that checks
//      whether the condition is true.
//      Default: null.  This means that the function blocks the execution until
//      the maxWaitTime expires (or until stop is requested).
//
//    pl_maxWaitTime - in *float* - the maximal time to wait for the condition to become true
//      Default: -1.0 which means infinity
//
//  Return Value:
//    *boolean* - true if the condition was fulfilled, false otherwise
//
//  Errors & assertions:
//    - 
//
//  Detailed Comments:
//    Can be used to block execution until the condition becomes true.
//    By calling this function the user can block execution until
//    a given event occurs ( = the event when the value returned
//    by the pl_checkCondFn function becomes true).
//    If it is called with a null pl_checkCondFn argument (default setting), the function
//    blocks the execution for pl_maxWaitTime seconds.
//
//    If the function is called with default arguments (function and max wait time is not given),
//    it behaves similarly to <f_EPTF_Base_wait4Shutdown>, i.e. it blocks the execution forever
//    (or until stop is requested).
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_waitForCondition(
  in EPTF_Base_CheckCondition_FT pl_checkCondFn := null,
  in float pl_maxWaitTime := -1.0
) return boolean {
  timer t_wait := 0.0;
  t_wait.start;
  timer t_periodicUpdate := 1.0; // needed to generate an event even if nothing happens
  if (pl_checkCondFn!=null) {
    t_periodicUpdate.start;
  }
  timer t_maxWait := 0.0;
  if (pl_maxWaitTime>0.0) {
    t_maxWait.start(pl_maxWaitTime);
  }
  alt {
    [pl_checkCondFn!=null and pl_checkCondFn.apply()] t_wait.timeout {
      return true; // condition fulfilled
    }
    [pl_maxWaitTime>0.0] t_maxWait.timeout;
    [pl_checkCondFn!=null] t_periodicUpdate.timeout {
      t_periodicUpdate.start;
      repeat;
    }
  }
  return false; // the alt exited before the condition was true
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_upcast
// 
//  Purpose:
//   Cast the component type from EPTF_Base_CT to integer
// 
//  Parameters:
//    pl_compRef - <EPTF_Base_CT> - the component to cast
//
//  Return Value:
//    integer - the casted component reference
//
//  Detailed Comments:
//    Actually accepts all components that extend <EPTF_Base_CT>
//
///////////////////////////////////////////////////////////
public external function f_EPTF_Base_upcast(in EPTF_Base_CT_private pl_compRef) return integer;

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_downcast
// 
//  Purpose:
//   Cast the component type from integer to EPTF_Base_CT
// 
//  Parameters:
//    pl_compRef - *integer* - the component to cast
//
//  Return Value:
//    EPTF_Base_CT - the casted component reference
//
///////////////////////////////////////////////////////////
public external function f_EPTF_Base_downcast(in integer pl_baseCompRef) return EPTF_Base_CT;

// private external functions for process info extraction
private external function f_EPTF_Base_getStartCmd() return charstring;

private external function f_EPTF_Base_getStartDir() return charstring;

private external function f_EPTF_Base_getEffectiveCmdline() return EPTF_CharstringList;

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_getRelTimeInSecs
// 
//  Purpose:
//    Get the relative time in seconds since component initialization.
//
//  Parameters:
//    -
//
//  Return Value:
//    float
//
//  Errors:
//    -
//
//  Detailed Comments:
//    -
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_getRelTimeInSecs()
runs on EPTF_Base_CT_private
return float
{
  return T_EPTF_componentClock.read;
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_getRelTimeOffsetInSecs
// 
//  Purpose:
//    Get the time offset in seconds (getTimeOfDay at component initialization)
//
//  Parameters:
//    -
//
//  Return Value:
//    float
//
//  Errors:
//    -
//
//  Detailed Comments:
//    -
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_getRelTimeOffsetInSecs()
runs on EPTF_Base_CT_private
return float
{
  return v_EPTF_Base_abstimeOfZeroComponentClock;
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_getAbsTimeInSecs
// 
//  Purpose:
//    Get the absolute time in seconds (~getTimeOfDay)
//
//  Parameters:
//    pl_relTime - *in pl_relTime* - relative time in secs since component initialization
//     if not specified (or <0) current time will be measured
//
//  Return Value:
//    float
//
//  Errors:
//    -
//
//  Detailed Comments:
//    The current pl_relTime can be determined by <f_EPTF_Base_getRelTimeInSecs>
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_getAbsTimeInSecs(in float pl_relTime := -1.0)
runs on EPTF_Base_CT_private
return float
{
  if (pl_relTime<0.0) {
    return v_EPTF_Base_abstimeOfZeroComponentClock + T_EPTF_componentClock.read;
  }
  return v_EPTF_Base_abstimeOfZeroComponentClock + pl_relTime;
}


///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_getTimeOfDay
// 
//  Purpose:
//   Returns the system time since 00:00 UCT, Jan 1, 1970
// 
//  Parameters:
//    -
//
//  Return Value:
//    float
//
//  Detailed Comments:
//    Used for initializing the time offset.
//    It is recommended to use f_EPTF_Base_getAbsTimeInSecs() instead to
//    get the current time.
///////////////////////////////////////////////////////////
public external function f_EPTF_Base_getTimeOfDay() return float;

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_setNegativeTestMode
// 
//  Purpose:
//    This function sets the negative test mode
//
//  Parameters:
//    pl_negativeTest - *in boolean* - if true: <f_EPTF_Base_assert> will not set the verdict,
//            if false: verdict is set by <f_EPTF_Base_assert>
//
//  Return Value:
//    -
//
//  Errors:
//    -
//
//  Detailed Comments:
//    It disables the setverdict in the functions: <f_EPTF_Base_stop>, <f_EPTF_Base_stopAll> and <f_EPTF_Base_assert>
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_setNegativeTestMode(in boolean pl_negativeTest := true) runs on EPTF_Base_CT_private {
  action(%definitionId&": THIS IS A NEGATIVE TEST, VERDICT SHOULD BE PASS!");
  v_EPTF_Base_negativeTestMode:= pl_negativeTest;
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_getNegativeTestMode
// 
//  Purpose:
//    This function returns the negative test mode
//
//  Parameters:
//
//  Return Value:
//    -
//
//  Errors:
//    -
//
//  Detailed Comments:
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_getNegativeTestMode() 
runs on EPTF_Base_CT_private
return boolean{
  return v_EPTF_Base_negativeTestMode;
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_assert
// 
//  Purpose:
//   Stop the component execution if the condition is false and print out a message.
// 
//  Parameters:
//    pl_assertMessage - *charstring* - the message printed out on error
//    pl_predicate - *boolean* - the condition that should be true, otherwise the component will be stopped
//
//  Return Value:
//    -
//
///////////////////////////////////////////////////////////
public external function f_EPTF_Base_assert(in charstring pl_assertMessage,in boolean pl_predicate);

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_addAssertMsg
// 
//  Purpose:
//   Adds the message to the assert messages list.
// 
//  Parameters:
//    pl_newMsg - *in charstring* - message to add
//
//  Return Value:
//    -
//
///////////////////////////////////////////////////////////
private function f_EPTF_Base_addAssertMsg(in charstring pl_newMsg) runs on EPTF_Base_CT_private {
  v_EPTF_Base_assertMsgs[sizeof(v_EPTF_Base_assertMsgs)] := pl_newMsg;
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_nofAssertMsgs
// 
//  Purpose:
//    Returns the number of assert messages generated by previous <f_EPTF_Base_assert> function calls.
// 
//  Parameters:
//    -
//
//  Return Value:
//    integer - the number of assert messages
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_nofAssertMsgs() runs on EPTF_Base_CT_private return integer {
  return sizeof(v_EPTF_Base_assertMsgs);
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_getAssertMsg
// 
//  Purpose:
//   Returns an assert message from the previous assert messages.
// 
//  Parameters:
//    pl_assertNum - *in integer* - the id of the assert message (0 for the first message)
//
//  Return Value:
//    charstring - the assert message, "" if not found
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_getAssertMsg(in integer pl_assertNum := 0) runs on EPTF_Base_CT_private return charstring {
  if (sizeof(v_EPTF_Base_assertMsgs)==0) {
    return "";
  }
  if (sizeof(v_EPTF_Base_assertMsgs)<=pl_assertNum or pl_assertNum<0) {
    return "";
  }
  return v_EPTF_Base_assertMsgs[pl_assertNum];
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_setExpectedAssertMsg
// 
//  Purpose:
//   Sets the assert message that is checked in cleanup if this was the first assert message.
// 
//  Parameters:
//    pl_expectedAssert - *in charstring* - the assert message pattern to expect as the first assert
//
//  Return Value:
//    -
//
//  Detailed Comments:
//    The expected assert pattern is automatically checked in <f_EPTF_Base_cleanup_CT>,
//    and the verdict is set automatically to pass if that matches with the first assert, and fail if it does not.
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_setExpectedAssertMsg(in charstring pl_expectedAssert) runs on EPTF_Base_CT_private {
  v_EPTF_Base_expectedAssert := pl_expectedAssert;
  if("" != v_EPTF_Base_expectedError){
    f_EPTF_Common_warning(%definitionId&": There is already an expected error message: "&v_EPTF_Base_expectedError&
    " This may cause ambiguous behavior!")
  }
  f_EPTF_Base_setNegativeTestMode()
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_setExpectedErrorMsg
// 
//  Purpose:
//   Sets the error message that is checked in cleanup if this was the first error message.
// 
//  Parameters:
//    pl_expectedError - *in charstring* - the error message pattern to expect as the first assert
//
//  Return Value:
//    -
//
//  Detailed Comments:
//    The expected assert pattern is automatically checked in <f_EPTF_Base_cleanup_CT>,
//    and the verdict is set automatically to pass if that matches with the first error, and fail if it does not.
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_setExpectedErrorMsg(in charstring pl_expectedError) runs on EPTF_Base_CT_private {
  v_EPTF_Base_expectedError := pl_expectedError;
  if("" != v_EPTF_Base_expectedAssert){
    f_EPTF_Common_warning(%definitionId&": There is already an expected assert message: "&v_EPTF_Base_expectedAssert&
    " This may cause ambiguous behavior!")
  }
  f_EPTF_Base_setNegativeTestMode()
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_checkExpectedAssert
// 
//  Purpose:
//   Checks if the expectedAssert message pl_expectedAssert was the assert message at pl_assertNum or not
// 
//  Parameters:
//    pl_expectedAssert - *in charstring* - the expected assert pattern
//    pl_assertNum - *in integer* - the id of the assert message (0 for the first message)
//
//  Return Value:
//    boolean - true if the expected assert pattern matches with the given assert
//
//  Detailed Comments:
//   This function is called automatically in the <f_EPTF_Base_cleanup_CT>
///////////////////////////////////////////////////////////
public function f_EPTF_Base_checkExpectedAssert(in charstring pl_expectedAssert, in integer pl_assertNum := 0)
runs on EPTF_Base_CT_private return boolean {
  if (not match(f_EPTF_Base_getAssertMsg(pl_assertNum), pattern pl_expectedAssert)) {
    f_EPTF_Common_warning("Warning: "&%definitionId& ": Assert message with id "&int2str(pl_assertNum)&" is different from the expected pattern: "&
      log2str(match(f_EPTF_Base_getAssertMsg(pl_assertNum), pattern pl_expectedAssert)));
    return false;
  } else {
    f_EPTF_Common_user(%definitionId& ": Assert message with id "&int2str(pl_assertNum)&" matches with the expected pattern: "& pl_expectedAssert);
    return true;
  }
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_checkExpectedError
// 
//  Purpose:
//   Checks if the expectedError message pl_expectedError was the error message at pl_errNum or not
// 
//  Parameters:
//    pl_expectedError - *in charstring* - the expected error pattern
//    pl_errNum - *in integer* - the id of the error message (0 for the first message)
//
//  Return Value:
//    boolean - true if the expected error pattern matches with the given error
//
//  Detailed Comments:
//   This function is called automatically in the <f_EPTF_Base_cleanup_CT>
///////////////////////////////////////////////////////////
public function f_EPTF_Base_checkExpectedError(in charstring pl_expectedError, in integer pl_errNum := 0)
runs on EPTF_Base_CT_private return boolean {
  if (not match(f_EPTF_Common_getErrorMsg(pl_errNum), pattern pl_expectedError)) {
    f_EPTF_Common_warning("Warning: "&%definitionId& ": Error message with id "&int2str(pl_errNum)&" is different from the expected pattern: "&
      log2str(match(f_EPTF_Common_getErrorMsg(pl_errNum), pattern pl_expectedError)));
    return false;
  } else {
    f_EPTF_Common_user(%definitionId& ": Error message with id "&int2str(pl_errNum)&" matches with the expected pattern: "& pl_expectedError);
    return true;
  }
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_getPid
// 
//  Purpose:
//   Returns the pid of the current process
// 
//  Parameters:
//    -
//
//  Return Value:
//    integer
//
//  Detailed Comments:
//    -
///////////////////////////////////////////////////////////
public external function f_EPTF_Base_getPid() return integer;

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_getHostName
// 
//  Purpose:
//   Returns the name of the current host
// 
//  Parameters:
//    -
//
//  Return Value:
//    charstring - name of the host
//
//  Detailed Comments:
//    -
///////////////////////////////////////////////////////////
public external function f_EPTF_Base_getHostName() return charstring;

///////////////////////////////////////////////////////////
//  Public Function: f_EPTF_Base_getComponentInfoByName
// 
//  Purpose:
//    Returns the component data for a given name
// 
//  Parameters:
//    pl_name - *in* *charstring* - the name of the component to find
//    pl_compInfo - *in* <EPTF_Base_ComponentInfo> - the info about the component
//
//  Returns:
//    integer - error code (zero if the result is valid, nonzero if error occured)
//
//  Detailed Comments:
//    If more than one component exists with the same name, the one that is found first is returned
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_getComponentInfoByName(in charstring pl_name, out EPTF_Base_ComponentInfo pl_compInfo)
runs on EPTF_Base_CT_private return integer {
  // check in local database
  for(var integer i:=0;  i < sizeof(v_EPTF_Base_componentInfoList); i:=i+1) {
    if (v_EPTF_Base_componentInfoList[i].selfName==pl_name) {
      pl_compInfo := v_EPTF_Base_componentInfoList[i];
      return 0;
    }
  }
  // if I am the mtc: entry not found:
  if (self == mtc) {
    return -1;
  } else {
    // send message to mtc and wait for the response
    timer t_semaphore := 0.0;
    timer t_maxWait := tsp_EPTF_Base_maxWaitTime;

    // allocate buffer for result:
    var integer vl_EPTF_Base_getCompInfoRequestSemaphore := sizeof(v_EPTF_Base_getCompInfoResult);
    v_EPTF_Base_getCompInfoResult[vl_EPTF_Base_getCompInfoRequestSemaphore] := c_EPTF_Base_Msg_GetCompInfoResult_init;

    //connect(self:EPTF_Base_MgmtIf,mtc:EPTF_Base_MgmtIf); // I will close the connection
    f_EPTF_Base_send({getCompInfo:={vl_EPTF_Base_getCompInfoRequestSemaphore,pl_name}},mtc);
    // wait for response:
    t_maxWait.start;
    t_semaphore.start;
    alt {
      [vl_EPTF_Base_getCompInfoRequestSemaphore==v_EPTF_Base_getCompInfoResult[vl_EPTF_Base_getCompInfoRequestSemaphore].msgId] t_semaphore.timeout {
        // response arrived:
        pl_compInfo := v_EPTF_Base_getCompInfoResult[vl_EPTF_Base_getCompInfoRequestSemaphore].compInfo;
        var integer vl_errorCode := v_EPTF_Base_getCompInfoResult[vl_EPTF_Base_getCompInfoRequestSemaphore].errorCode;
        //disconnect(self:EPTF_Base_MgmtIf,mtc:EPTF_Base_MgmtIf); // I will close the connection
        if (vl_errorCode==0) {
          // add new entry to local database
          f_EPTF_Base_addComponentInfo(pl_compInfo.compRef,pl_compInfo.selfName,pl_compInfo.hostName,pl_compInfo.pid);
        }
        v_EPTF_Base_getCompInfoResult[vl_EPTF_Base_getCompInfoRequestSemaphore] := c_EPTF_Base_Msg_GetCompInfoResult_init; // release semaphore
        return vl_errorCode; // OK
      }
      [] t_maxWait.timeout {
        f_EPTF_Common_warning(%definitionId& ": MaxWaitTime expired to wait for getCompInfo response. Current request failed.");
        //disconnect(self:EPTF_Base_MgmtIf,mtc:EPTF_Base_MgmtIf); // I will close the connection
        v_EPTF_Base_getCompInfoResult[vl_EPTF_Base_getCompInfoRequestSemaphore] := c_EPTF_Base_Msg_GetCompInfoResult_init; // release semaphore
        return -3; // cannot get compInfo, previous request is pending
      }
    }
  }
  return -1; // not found
}

///////////////////////////////////////////////////////////
//  Public Function: f_EPTF_Base_getPidByName
// 
//  Purpose:
//    Returns the component data for a given name
// 
//  Parameters:
//    pl_name - *in* *charstring* - the name of the component to find
//
//  Returns:
//    integer - pid of the component with the given selfName (-1 if not available)
//
//  Detailed Comments:
//    If more than one component exists with the same name, the one that is found first is returned
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_getPidByName(in charstring pl_name)
runs on EPTF_Base_CT_private return integer {
  var EPTF_Base_ComponentInfo vl_compInfo;
  if (0==f_EPTF_Base_getComponentInfoByName(pl_name,vl_compInfo)) {
    return vl_compInfo.pid;
  } else {
    return -1; // not found
  }
}

///////////////////////////////////////////////////////////
//  Public Function: f_EPTF_Base_getComponentInfoAll
// 
//  Purpose:
//    Returns the component data for a given name
// 
//  Parameters:
//    -
//
//  Returns:
//    EPTF_Base_ComponentInfoList - list of all components
//
//  Detailed Comments:
//    -
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_getComponentInfoAll()
runs on EPTF_Base_CT_private return EPTF_Base_ComponentInfoList {
  // if I am the mtc: entry not found:
  if (self == mtc) {
    return v_EPTF_Base_componentInfoList;
  } else {
    // send message to mtc and wait for the response
    timer t_semaphore := 0.0;
    timer t_maxWait := tsp_EPTF_Base_maxWaitTime;

    // allocate buffer for result:
    var integer vl_EPTF_Base_getCompInfoRequestSemaphore := sizeof(v_EPTF_Base_getCompInfoResult);
    v_EPTF_Base_getCompInfoResult[vl_EPTF_Base_getCompInfoRequestSemaphore] := c_EPTF_Base_Msg_GetCompInfoResult_init;

    //connect(self:EPTF_Base_MgmtIf,mtc:EPTF_Base_MgmtIf); // I will close the connection
    f_EPTF_Base_send({getCompInfoAll:={vl_EPTF_Base_getCompInfoRequestSemaphore}},mtc);
    // wait for response:
    t_maxWait.start;
    t_semaphore.start;
    alt {
      [vl_EPTF_Base_getCompInfoRequestSemaphore==v_EPTF_Base_getCompInfoResult[vl_EPTF_Base_getCompInfoRequestSemaphore].msgId] t_semaphore.timeout {
        // response arrived:
        //disconnect(self:EPTF_Base_MgmtIf,mtc:EPTF_Base_MgmtIf); // I will close the connection
        v_EPTF_Base_getCompInfoResult[vl_EPTF_Base_getCompInfoRequestSemaphore] := c_EPTF_Base_Msg_GetCompInfoResult_init; // release semaphore
        return v_EPTF_Base_componentInfoList; // OK
      }
      [] t_maxWait.timeout {
        f_EPTF_Common_warning(%definitionId& ": MaxWaitTime expired to wait for getCompInfo response. Current request failed.");
        //disconnect(self:EPTF_Base_MgmtIf,mtc:EPTF_Base_MgmtIf); // I will close the connection
        v_EPTF_Base_getCompInfoResult[vl_EPTF_Base_getCompInfoRequestSemaphore] := c_EPTF_Base_Msg_GetCompInfoResult_init; // release semaphore
        return {}; // cannot get compInfo, previous request is pending
      }
    }
  }
  return {}; // not found
}

///////////////////////////////////////////////////////////
//  Public Function: f_EPTF_Base_setDTEHandling
// 
//  Purpose:
//    Sets the DTE handling flag to the given value
// 
//  Parameters:
//    pl_dteHandling - *in* *boolean* - if true DTE handling will be enabled,
//      otherwise it will be disabled
//
//  Returns:
//    -
//
//  Detailed Comments:
//    See more details at the function <f_EPTF_Base_isEnabledDTEHandling>
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_setDTEHandling(in boolean pl_dteHandling)
runs on EPTF_Base_CT_private {
  v_EPTF_Base_enableDTEHandling := pl_dteHandling;
}

///////////////////////////////////////////////////////////
//  Public Function: f_EPTF_Base_isEnabledDTEHandling
// 
//  Purpose:
//    Returns the true if DTE handling is enabled
// 
//  Parameters:
//    pl_dteHandling - *in* *boolean* - if true DTE handling will be enabled,
//      otherwise it will be disabled
//
//  Returns:
//    -
//
//  Detailed Comments:
//    When DTE handling is enabled, other CLL features that
//    support DTE handling (e.g. LGenBase, Scheduler, Transport)
//    will not stop when DTE occurs in user callback functions.
//    Instead they will print the error message as warning,
//    call a user given handler function, and continue the execution.
//    By default DTE handling is switched on.
//    To enable/disable DTE handling call the function 
//    <f_EPTF_Base_setDTEHandling>
//
//    Please note, that Titan versions before TITAN/4/R2A including this version
//    will not print the call stack of the actual place of the error.
//    Newer Titan version will support this.
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_isEnabledDTEHandling()
runs on EPTF_Base_CT_private return boolean {
  return v_EPTF_Base_enableDTEHandling;
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_system
//
//  Purpose:
//   Execute system command from TTCN
//
//  Parameters:
//   pl_command - *in* *charstring* - the name of the script/command to execute
//
//  Return Value:
//    -
//
//  Detailed Comments:
//    -
//
///////////////////////////////////////////////////////////
public external function f_EPTF_Base_system(in charstring pl_command) return integer;

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_executeShell
//
//  Purpose:
//   Execute shell script from TTCN
//
//  Parameters:
//   pl_command - *in* *charstring* - the name of the script/command to execute
//   pl_stdOut - *out* *charstring* - standard output
//   pl_stdErr - *out* *charstring* - standard error
//   pl_enableAlts - *out* *boolean* - if true, default altsteps can run during the function call
//
//  Return Value:
//    *integer* - error code, zero if execution is successful
//
//  Detailed Comments:
//    -
//
///////////////////////////////////////////////////////////
public external function f_EPTF_Base_executeShell(
  in charstring pl_command,
  out charstring pl_stdOut,
  out charstring pl_stdErr,
  in boolean pl_enableAlts := true) return integer;

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_getStartCommand
//
//  Purpose:
//   Returns with the start command which is needed for restart
//
//  Parameters:
//   pl_executable - *out* *charstring* - executable
//   pl_configFile - *out* *charstring* - config file
//   pl_testCases - *out* *EPTF_CharstringList* - test case list
//
//  Return Value:
//    *charstring* - whole start command
//
//  Errors:
//    -
//
//  Detailed Comments:
//    example start command: "/app/TITAN/5_R3A/LMWP3.1/bin/ttcn3_start EPTF_Base_Test ../EPTF_Base_Test.cfg EPTF_Base_Test_Testcases.tc_EPTF_Base_Test_getStartCommand"
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_getStartCommand(
  out charstring pl_executable,
  out charstring pl_configFile,
  out EPTF_CharstringList pl_testCases) runs on EPTF_Base_CT_private return charstring {

  pl_executable := f_EPTF_Base_getStartCmd();
  pl_configFile := "";
  pl_testCases := {};

  var EPTF_CharstringList vl_cmdline := f_EPTF_Base_getEffectiveCmdline();
  var integer vl_cmdline_size := sizeof(vl_cmdline);
  var integer vl_currentIdx := 2;
  if(vl_cmdline_size >= 3){
    // check if the config was given in the start command
    if(match(vl_cmdline[2], pattern "*.cfg")){
      pl_configFile := vl_cmdline[2];
      vl_currentIdx := 3;
    }
  }
  if (pl_configFile == "") {
    // check if default config exists
    var charstring vl_configFile := pl_executable & ".cfg";
    var charstring vl_existsStdOut;
    var charstring vl_existsStdErr;
    if (f_EPTF_Base_executeShell("bash -c \"if [ -e " & vl_configFile & " ]; then echo -n 0; else echo -n 1; fi\"", vl_existsStdOut, vl_existsStdErr) == 0) {
      if (vl_existsStdOut == "0") {
        pl_configFile := vl_configFile;
      }
    } else {
      f_EPTF_Common_warning(%definitionId & ": Default config file existence check failed, because of : " & vl_existsStdErr);
    }
  }
  
  // collecting test cases from the command
  if(vl_cmdline_size >= vl_currentIdx + 1) {
    for(var integer vl_i := vl_currentIdx; vl_i < vl_cmdline_size; vl_i := vl_i + 1){
      pl_testCases[sizeof(pl_testCases)] := vl_cmdline[vl_i];
    }
  }
  
  var charstring vl_cmdline_flatten := "";
  for (var integer vl_i := 0; vl_i < vl_cmdline_size; vl_i := vl_i + 1){
    vl_cmdline_flatten := vl_cmdline_flatten & vl_cmdline[vl_i] & " ";
  }

  return vl_cmdline_flatten;
}

///////////////////////////////////////////////////////////
//  Function: f_EPTF_Base_restart
//
//  Purpose:
//   Restarts the application
//
//  Parameters:
//   pl_executable - *in* *charstring* - executable
//   pl_configFile - *in* *charstring* - configuration file
//   pl_testCases - *in* <EPTF_CharstringList> - test case list
//
//  Return Value:
//
//  Errors:
//    -
//
//  Detailed Comments:
//    -
//
///////////////////////////////////////////////////////////
public function f_EPTF_Base_restart(
  in charstring pl_executable := "-",
  in charstring pl_configFile := "-",
  in EPTF_CharstringList pl_testCases := {"-"}) runs on EPTF_Base_CT_private {

  var charstring vl_stdOut := "";
  var charstring vl_stdErr := "";
  var charstring vl_command := "";

  var charstring vl_startCmd := ""
  var charstring vl_executable := "";
  var charstring vl_configFile := "";
  var EPTF_CharstringList vl_testCases := {};

  var EPTF_CharstringList vl_startCommandString := f_EPTF_Common_splitString(f_EPTF_Base_getStartCommand(vl_executable, vl_configFile, vl_testCases), " ");
  // default values of incoming parameters are hyphen string which means that the original parameters (which comes from f_EPTF_Base_getStartCommand) will be used for restart
  if(pl_executable != "-"){
    vl_executable := pl_executable;
  }
  if(pl_configFile != "-"){
    vl_configFile := pl_configFile;
  }
  if(pl_testCases != {"-"}){
    vl_testCases := pl_testCases;
  }
  if(sizeof(vl_startCommandString)>0 and lengthof(vl_startCommandString[0]) > 0){
   vl_startCmd := vl_startCommandString[0];
  }

  var charstring vl_ttcn3Dir := regexp(vl_startCmd,"(*)bin/ttcn3_start",0);
  var charstring vl_waitString := "while [ -e /proc/"&int2str(f_EPTF_Base_getPid())&" ]; do sleep 0.1; done;";
  var charstring vl_setEnvTtcn3Dir := "export TTCN3_DIR="&vl_ttcn3Dir&";" // TTCN3_DIR needs to be set to its original value beceause of new tcsh shell
  var charstring vl_restartCommand := vl_waitString &" "& vl_setEnvTtcn3Dir& vl_startCmd&" "&vl_executable&" "&vl_configFile;
  for(var integer vl_i := 0; vl_i < sizeof(vl_testCases); vl_i := vl_i + 1){
    vl_restartCommand := vl_restartCommand&" "&vl_testCases[vl_i];
  }

  vl_command := "bash -c \"nohup xterm -e /bin/bash -c '"&vl_restartCommand&"' >/dev/null 2>&1 &\"";
  if(f_EPTF_Base_executeShell(vl_command, vl_stdOut, vl_stdErr) != 0){
    f_EPTF_Common_warning(%definitionId& ": Could not restart with command: "&vl_command&" because of: "&vl_stdErr);
  }

  f_EPTF_Base_stopAll(none);
}

} // group public

//*************************************************************
//  private
//*************************************************************


// this function was public, but had incorrect name. Use f_EPTF_Base_registerCleanup instead.
/*public*/ function f_EPTF_Base_RegisterCleanup(in f_EPTF_Feature_cleanup_CT pl_featureCleanupFn) runs on EPTF_Base_CT_private {
  f_EPTF_Common_warning("Warning: "&%definitionId& ": This function is deprecated and will be removed! Use f_EPTF_Base_registerCleanup instead!");
  f_EPTF_Base_registerCleanup(pl_featureCleanupFn);
}

///////////////////////////////////////////////////////////
//  Private Function: f_EPTF_Base_addComponentInfo
// 
//  Purpose:
//    Adds a component to the known component list
// 
//  Parameters:
//    -
//
//  Detailed Comments:
//    The component list is used for stopping the added components at cleanup.
//
///////////////////////////////////////////////////////////
private function f_EPTF_Base_addComponentInfo(in EPTF_Base_CT pl_remoteCompRef, in charstring pl_name, in charstring pl_hostName, in integer pl_pid) runs on EPTF_Base_CT_private {
  var integer vl_i := sizeof(v_EPTF_Base_componentInfoList);
  v_EPTF_Base_componentInfoList[vl_i] := {pl_name,pl_remoteCompRef,pl_hostName,pl_pid};
}

///////////////////////////////////////////////////////////
//  Private Function: f_EPTF_Base_addComponent
// 
//  Purpose:
//    Adds a component to the known component list
// 
//  Parameters:
//    -
//
//  Detailed Comments:
//    The component list is used for stopping the added components at cleanup.
//
///////////////////////////////////////////////////////////
private function f_EPTF_Base_addComponent(in EPTF_Base_CT pl_remoteCompRef) runs on EPTF_Base_CT_private {
  var integer vl_i := sizeof(v_EPTF_Base_componentsToStop) - 1;
  while(vl_i >= 0 and v_EPTF_Base_componentsToStop[vl_i] == null) {
    vl_i := vl_i - 1;
  }
  vl_i := vl_i + 1;
  v_EPTF_Base_componentsToStop[vl_i] := pl_remoteCompRef;
}

private function f_EPTF_Base_removeComponent(in EPTF_Base_CT_private pl_remoteCompRef) runs on EPTF_Base_CT_private {
  for (var integer i:=0; i<sizeof(v_EPTF_Base_componentsToStop); i := i+1) {
    if ( v_EPTF_Base_componentsToStop[i] == pl_remoteCompRef) {
      v_EPTF_Base_componentsToStop[i] := null;
      return;
    }
  }
}

private function f_EPTF_Base_stopAllComponents() runs on EPTF_Base_CT_private {
  v_EPTF_Base_stopRemoteSentTo:=mtc; // to notify the altstep about stopping all components, The value mtc is set only here
  // stop backwards:
  for (var integer i:=sizeof(v_EPTF_Base_componentsToStop)-1; i>=0; i := i-1) {
    if ( v_EPTF_Base_componentsToStop[i] != null) {
      var EPTF_Base_CT vl_componentToStop := v_EPTF_Base_componentsToStop[i];
      f_EPTF_Base_stopRemote(v_EPTF_Base_componentsToStop[i]); // always with cleanup: this is not called if stopping without cleanup
      if (v_EPTF_Base_serialStopAllComponents) {
        // wait for the component to terminate:
        vl_componentToStop.done;
        i:=sizeof(v_EPTF_Base_componentsToStop)-1; // restart the for cycle because bye or stopRemote messages might have arrived during waiting
      }
    }
  }
}

// stops the last created component
// if all components terminated it stops itself (the mtc)
private function f_EPTF_Base_stopLastComponent() runs on EPTF_Base_CT_private{
  if (self!=mtc) {
    return; // this function works only on mtc
  }

  // stop backwards:
  for (var integer i:=sizeof(v_EPTF_Base_componentsToStop)-1; i>=0; i := i-1) {
    if ( v_EPTF_Base_componentsToStop[i] != null) {
      var EPTF_Base_CT vl_componentToStop := v_EPTF_Base_componentsToStop[i];
      f_EPTF_Base_stopRemote(v_EPTF_Base_componentsToStop[i]); // always with cleanup: this is not called if stopping without cleanup
      v_EPTF_Base_stopRemoteSentTo := vl_componentToStop;
      return;
    }
  }
  // all components stopped
  // stopping myself:
  if (tsp_EPTF_Base_debug){
    f_EPTF_Common_user(log2str("All components terminated. Stopping myself (MTC)..."));
  }
  f_EPTF_Base_cleanup_CT();
  stop;
}


// SEND FUNCTION

private function f_EPTF_Base_send(in EPTF_Base_MgmtMsg pl_EPTF_Base_MgmtMsg, in EPTF_Base_CT_private pl_remoteCompRef) runs on EPTF_Base_CT_private {
  @try {
    EPTF_Base_MgmtIf.send(pl_EPTF_Base_MgmtMsg) to pl_remoteCompRef;
  } @catch(dte_str) {
    f_EPTF_Base_removeComponent(pl_remoteCompRef);
  }
}

private function f_EPTF_Base_handle_StopRemote(in EPTF_Base_Msg_StopRemote pl_stopRemote, in EPTF_Base_CT_private pl_EPTF_Base_MgmtIf_msg_sender) runs on EPTF_Base_CT_private {
  if (v_EPTF_Base_initialized == false) {
    f_EPTF_Common_warning(log2str("Warning:","Cleanup is in progress, stopRemote message dropped."));
    if (self == mtc) {
      // however, the remote component should be removed from database, since that decided to exit by itself:
      //f_EPTF_Base_removeComponent(pl_EPTF_Base_MgmtIf_msg_sender); // StopRemote with wait4Shutdown
    }
    return; // do not exit alt loop now: cleanup is in progress, stopRemote message is dropped!
  }
  if (tsp_EPTF_Base_debug){
    f_EPTF_Common_user(log2str("StopRemote received from ",pl_EPTF_Base_MgmtIf_msg_sender,". Trying to stop execution gracefully..."));
  }
  if (self != mtc) {
    disconnect(self:EPTF_Base_MgmtIf,pl_EPTF_Base_MgmtIf_msg_sender:EPTF_Base_MgmtIf);
  }
  if (pl_stopRemote.noCleanup) {
    f_EPTF_Common_warning(log2str("Warning:","Cleanup is disabled in stopRemote message. CLEANUP IS NOT PERFORMED."));
  } else {
    if (pl_EPTF_Base_MgmtIf_msg_sender == mtc) {
      v_EPTF_Base_disableBye := true;
    } 
    if (self == mtc) {
      // sender wants me to stop and I am the mtc: sender is already terminated
      //f_EPTF_Base_removeComponent(pl_EPTF_Base_MgmtIf_msg_sender); // StopRemote with wait4Shutdown
      if (v_EPTF_Base_serialStopAllComponents) {
        f_EPTF_Base_stopLastComponent(); // stopping of components initiated one by one
      } else {
        f_EPTF_Base_stopAllComponents(); // stopping all components at the same time
      }
      return; // mtc is not killed. it will be killed after all components have terminated
    }
    f_EPTF_Base_cleanup_CT();
  }
  stop; // terminate the component now
}

private function f_EPTF_Base_handle_hello(in EPTF_Base_Msg_Hello pl_msgHello, in EPTF_Base_CT pl_EPTF_Base_MgmtIf_msg_sender) runs on EPTF_Base_CT_private {
  f_EPTF_Base_addComponent(pl_EPTF_Base_MgmtIf_msg_sender);
  f_EPTF_Base_addComponentInfo(pl_EPTF_Base_MgmtIf_msg_sender,pl_msgHello.myName,pl_msgHello.myHostName,pl_msgHello.myPid);
}

private function f_EPTF_Base_handle_getCompInfo(in EPTF_Base_Msg_GetCompInfo pl_msgGetCompInfo, in EPTF_Base_CT pl_EPTF_Base_MgmtIf_msg_sender) runs on EPTF_Base_CT_private {
  // i am the mtc
  var EPTF_Base_ComponentInfo vl_compInfo;
  var integer vl_errorCode := f_EPTF_Base_getComponentInfoByName(pl_msgGetCompInfo.selfName, vl_compInfo);
  if (vl_errorCode!=0) {
    vl_compInfo := c_EPTF_Base_ComponentInfo_init;
  }
  f_EPTF_Base_send({getCompInfoResult:={
    pl_msgGetCompInfo.msgId,
    vl_compInfo,
    vl_errorCode
  }},pl_EPTF_Base_MgmtIf_msg_sender)
}

private function f_EPTF_Base_handle_getCompInfoResult(in EPTF_Base_Msg_GetCompInfoResult pl_msgGetCompInfo, in EPTF_Base_CT pl_EPTF_Base_MgmtIf_msg_sender) runs on EPTF_Base_CT_private {
  // i am not the mtc
  v_EPTF_Base_getCompInfoResult[pl_msgGetCompInfo.msgId] := pl_msgGetCompInfo;
}

private function f_EPTF_Base_handle_getCompInfoAll(in EPTF_Base_Msg_GetCompInfoAll pl_msgGetCompInfoAll, in EPTF_Base_CT pl_EPTF_Base_MgmtIf_msg_sender) runs on EPTF_Base_CT_private {
  // i am the mtc
  f_EPTF_Base_send({getCompInfoAllResult:={
    pl_msgGetCompInfoAll.msgId,
    v_EPTF_Base_componentInfoList
  }},pl_EPTF_Base_MgmtIf_msg_sender)
}

private function f_EPTF_Base_handle_getCompInfoAllResult(in EPTF_Base_Msg_GetCompInfoAllResult pl_msgGetCompInfoAll, in EPTF_Base_CT pl_EPTF_Base_MgmtIf_msg_sender) runs on EPTF_Base_CT_private {
  // i am not the mtc
  v_EPTF_Base_getCompInfoResult[pl_msgGetCompInfoAll.msgId].msgId := pl_msgGetCompInfoAll.msgId;
  // overwrite the local database:
  v_EPTF_Base_componentInfoList := pl_msgGetCompInfoAll.compInfoAll;
}

private function f_EPTF_Base_handle_bye(in EPTF_Base_CT pl_EPTF_Base_MgmtIf_msg_sender) runs on EPTF_Base_CT_private {
  f_EPTF_Base_removeComponent(pl_EPTF_Base_MgmtIf_msg_sender);
  f_EPTF_Base_send({byeAck := {}},pl_EPTF_Base_MgmtIf_msg_sender);
}

private function f_EPTF_Base_handle_byeAck(in EPTF_Base_CT pl_EPTF_Base_MgmtIf_msg_sender) runs on EPTF_Base_CT_private {
  v_EPTF_Base_byeAckReceived := true;
}

modulepar float tsp_EPTF_Base_maxWaitTime := 120.0;

private function f_EPTF_Base_waitForByeAck() runs on EPTF_Base_CT_private {
  timer t_wait := 0.0;
  t_wait.start;
  timer t_maxWait := tsp_EPTF_Base_maxWaitTime;
  t_maxWait.start;
  alt {
    [v_EPTF_Base_byeAckReceived] t_wait.timeout;
    [] t_maxWait.timeout {
      f_EPTF_Common_warning(%definitionId&": ByeAck is not received before max wait time expired. Continuing anyway...");
    }
  }
}

// the main handler function of the EPTF_Var_MgmtIf.
// returns true if the repeat, false to exit from the main altsep
private function f_handle_main_EPTF_Base_MgmtIf(
  in EPTF_Base_MgmtMsg vl_EPTF_Base_MgmtIf_msg,
  in EPTF_Base_CT vl_EPTF_Base_MgmtIf_msg_sender) runs on EPTF_Base_CT_private return boolean {
  if (ischosen(vl_EPTF_Base_MgmtIf_msg.stopRemote)) {
    f_EPTF_Base_handle_StopRemote(vl_EPTF_Base_MgmtIf_msg.stopRemote,vl_EPTF_Base_MgmtIf_msg_sender);
    return true; // if this code is executed: do not exit from the alt-loop!
  }
  if (ischosen(vl_EPTF_Base_MgmtIf_msg.hello)) {
    f_EPTF_Base_handle_hello(vl_EPTF_Base_MgmtIf_msg.hello,vl_EPTF_Base_MgmtIf_msg_sender);
    return true;
  }
  if (ischosen(vl_EPTF_Base_MgmtIf_msg.getCompInfo)) {
    f_EPTF_Base_handle_getCompInfo(vl_EPTF_Base_MgmtIf_msg.getCompInfo,vl_EPTF_Base_MgmtIf_msg_sender);
    return true;
  }
  if (ischosen(vl_EPTF_Base_MgmtIf_msg.getCompInfoResult)) {
    f_EPTF_Base_handle_getCompInfoResult(vl_EPTF_Base_MgmtIf_msg.getCompInfoResult,vl_EPTF_Base_MgmtIf_msg_sender);
    return true;
  }
  if (ischosen(vl_EPTF_Base_MgmtIf_msg.getCompInfoAll)) {
    f_EPTF_Base_handle_getCompInfoAll(vl_EPTF_Base_MgmtIf_msg.getCompInfoAll,vl_EPTF_Base_MgmtIf_msg_sender);
    return true;
  }
  if (ischosen(vl_EPTF_Base_MgmtIf_msg.getCompInfoAllResult)) {
    f_EPTF_Base_handle_getCompInfoAllResult(vl_EPTF_Base_MgmtIf_msg.getCompInfoAllResult,vl_EPTF_Base_MgmtIf_msg_sender);
    return true;
  }
  if (ischosen(vl_EPTF_Base_MgmtIf_msg.bye)) {
    f_EPTF_Base_handle_bye(vl_EPTF_Base_MgmtIf_msg_sender);
    return true;
  }
  if (ischosen(vl_EPTF_Base_MgmtIf_msg.byeAck)) {
    f_EPTF_Base_handle_byeAck(vl_EPTF_Base_MgmtIf_msg_sender);
    return true;
  }
  // this is never reached:
  f_EPTF_Common_error(log2str("ERROR:","Unexpected message received from ",vl_EPTF_Base_MgmtIf_msg_sender,": ",vl_EPTF_Base_MgmtIf_msg));
  return false;
}

private altstep as_EPTF_Base_stopAllComponents() runs on EPTF_Base_CT_private {
  [self==mtc and v_EPTF_Base_stopRemoteSentTo!=null and v_EPTF_Base_stopRemoteSentTo!=mtc] v_EPTF_Base_stopRemoteSentTo.done {
    f_EPTF_Base_stopLastComponent(); // if none remains this will not return
    repeat;
  }
  [self==mtc and v_EPTF_Base_stopRemoteSentTo==mtc and v_EPTF_Base_initialized] all component.done {
    f_EPTF_Base_stopLastComponent(); // only mtc is alive => stop it
    repeat;
  }
}

private altstep as_handle_main_EPTF_Base_MgmtIf() runs on EPTF_Base_CT_private {
  var EPTF_Base_MgmtMsg vl_EPTF_Base_MgmtIf_msg;
  var EPTF_Base_CT vl_EPTF_Base_MgmtIf_msg_sender;
  [] EPTF_Base_MgmtIf.receive(?) -> value vl_EPTF_Base_MgmtIf_msg sender vl_EPTF_Base_MgmtIf_msg_sender {
    if (f_handle_main_EPTF_Base_MgmtIf(vl_EPTF_Base_MgmtIf_msg,vl_EPTF_Base_MgmtIf_msg_sender)) {repeat;}
  }
  [] as_EPTF_Base_stopAllComponents();
}

} // end of module
