'#Uses "..\include\Global.inc"
'#Uses "..\include\Const.inc"
'#Uses "..\classes\FunctionClass.cls"
'#Uses "..\classes\ParameterClass.cls"
'#Uses "..\include\Format.inc"
'#Uses "..\include\Port.inc"

Option Explicit

'*****************************************************************************
' Module:
'        CANx
'-----------------------------------------------------------------------------
' Description:
'        This module contains all functions that are used in the 
'        CANx dialog script and in the CANx codegenerator script.
'
'-----------------------------------------------------------------------------
' History:
'                 
'        Rev. Author         Date        Description
'        ---------------------------------------------------------------------
'        1.0   ahe         16.06.00     final version for C167CS
'             
'        ---------------------------------------------------------------------
'        1.1   ahe         03.08.00     final version for C167CS
'                                       - no changes
'
'        ---------------------------------------------------------------------
'        2.0   ahe         08.08.00     final version for C161CS/JC
'                                       - check if XPERCON exist
'
'*****************************************************************************


'*****************************************************************************
' Constants
'*****************************************************************************

'*****************************************************************************
'Description:
'        For each function which should be used for this module a line 
'        "If (Not func.AddFunction .." must be insert in this function.
'        For each parameter that should be used for this function a  
'        line "If (Not func.AddParameter .." must be insert in this function.
'
'        Note:
'        For each added function a project variable with the name 
'        "CANx_NAME_Functionname" must be exist in the *.vars file. 
'-----------------------------------------------------------------------------
'Parameters:
'        func             reference to the FunctionClass object
'        r                reference to the Registers object
'-----------------------------------------------------------------------------
'Returns:
'        True            on successfull operation
'        False           else
'*****************************************************************************
Public Function RefreshFunctionDescriptions(vIndex As Variant, func As FunctionClass, r As ProjectData) As Boolean
  On Error Resume Next 

  RefreshFunctionDescriptions = False

  Dim sDescription As String
  Dim sReturnValue As String
  Dim sVarPre As String
  Dim sFctName As String
  Dim i As Integer

  sVarPre = "CAN" & vIndex


  ' for each function of this module the property AddFunction must be called
  '
  ' AddFunction(sFuncName As String, sFuncType As String, sFuncDescription As String, 
  '             sReturnvalue As String, lSort As Long) As Boolean
  '
  ' sFuncName          | String | function name as key (use the name of the variable 
  '                               for the function name e.g. SSC_NAME_Init) 
  ' sFuncType          | String | type of the function
  ' sFuncDescription   | String | description of the function
  ' sReturnvalue       | String | description of the return value
  ' lSort              | Long   | ' sort of the function (0 => macro, 1 => function, 2 => ISR, 3 => TRAP)

    ' for each parameter of a function the property AddParameter must be called
    '
    'AddParameter(sParName As String, sPar As String, sParType As String, sParDescription As String) As Boolean    
    '
    ' sParName         | String | parameter name (key)
    ' sPar             | String | parameter name
    ' sParType         | String | type of the parameter
    ' sParDescription  | String | description of the parameter

    'sDescription = ""
    'If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para1", "Var", "Typ", sDescription)) Then Exit Function


  '------------------------------------------------------------------------------------------------
  ' Description for CANx_NAME_Init
  '------------------------------------------------------------------------------------------------
  sDescription = GetGeneralInitDescription(sVarPre)
  
  sReturnValue = "None" 
  
  If (Not func.AddFunction(sVarPre & "_NAME_Init", "void", sDescription, sReturnValue, 1)) Then Exit Function

  '------------------------------------------------------------------------------------------------
  ' Description for CANx_NAME_...
  '------------------------------------------------------------------------------------------------
  sFctName = sVarPre
  sDescription = "This is the interrupt service routine for the " & sVarPre & " controller. " & _
                 "Depending on the configuration it is executed if:" & vbcrlf & _
                 "- the busoff or the error warning status is reached " & vbcrlf & _
                 "  (EIE is set)" & vbcrlf & _
                 "- a message has been sent or received successfully or a bus " & vbcrlf & _
                 "  error occurred (SIE is set)" & vbcrlf & _
                 "- the bit INTPND (interrupt pending) in one of the message " & vbcrlf & _
                 "  object control-registers is set (at Tx or Rx)"

                 sDescription = sDescription & vbcrlf & TOOLTIP_ISR_USERCODE

  sReturnValue = "None"
  If (Not func.AddFunction(sVarPre & "_NAME_" & sFctName, "void", sDescription, sReturnValue, 2)) Then Exit Function
 
  '------------------------------------------------------------------------------------------------
  ' Description for CANx_NAME_...
  '------------------------------------------------------------------------------------------------
  sFctName = "GetMsgObj"
  sDescription = "This function fills the forwarded SW message object with the " & _
                 "content of the chosen HW message object." & vbcrlf & _
                 "" & vbcrlf & _
                 "The structure of the SW message object is defined in the " & vbcrlf & _
                 "header file " & r.v(sVarPre & "_HFILE") & " (see T" & sVarPre & "_Obj)."

  sReturnValue = "None"
  If (Not func.AddFunction(sVarPre & "_NAME_" & sFctName, "void", sDescription, sReturnValue, 1)) Then Exit Function
    sDescription = "Number of the message object to be read (1-15)"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para1", "ubObjNr", "ubyte", sDescription)) Then Exit Function
    sDescription = "Pointer on a message object to be filled by this function"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para2", "*pstObj", "T" & sVarPre & "_Obj", sDescription)) Then Exit Function

  '------------------------------------------------------------------------------------------------
  ' Description for CANx_NAME_...
  '------------------------------------------------------------------------------------------------
  sFctName = "RequestMsgObj"
  sDescription = "If a TRANSMIT OBJECT is to be reconfigured it must first be " & _
                 "accessed. The access to the transmit object is exclusive. " & _
                 "This function checks whether the choosen message object is " & _
                 "still executing a transmit request, or if the object can " & _
                 "be accessed exclusively." & vbcrlf & _
                 "After the message object is reserved, it can be reconfigured " & _
                 "by using the function " & r.v(sVarPre & "_NAME_ConfigMsgObj") & " or " & _
                 r.v(sVarPre & "_NAME_LoadData") & "." & vbcrlf & _
                 "Both functions enable access to the object for the " & sVarPre & _
                 " controller. " & vbcrlf & _
                 "By calling the function " & r.v(sVarPre & "_NAME_Transmit") & " transfering of data " & _
                 "is started."

  sReturnValue = "0 message object is busy (a transfer is active), else 1"
  If (Not func.AddFunction(sVarPre & "_NAME_" & sFctName, "ubyte", sDescription, sReturnValue, 1)) Then Exit Function
    sDescription = "Number of the message object (1-14)"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para1", "ubObjNr", "ubyte", sDescription)) Then Exit Function
 
  '------------------------------------------------------------------------------------------------
  ' Description for CANx_NAME_...
  '------------------------------------------------------------------------------------------------
  sFctName = "NewData"
  sDescription = "This function checks whether the selected RECEIVE OBJECT has " & _
                 "received a new message. If so the function returns the " & _
                 "value '1'."

  sReturnValue = "1 the message object has received a new message, else 0"
  If (Not func.AddFunction(sVarPre & "_NAME_" & sFctName, "ubyte", sDescription, sReturnValue, 1)) Then Exit Function
    sDescription = "Number of the message object (1-15)"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para1", "ubObjNr", "ubyte", sDescription)) Then Exit Function
 
  '------------------------------------------------------------------------------------------------
  ' Description for CANx_NAME_...
  '------------------------------------------------------------------------------------------------
  sFctName = "Transmit"
  sDescription = "This function triggers the " & sVarPre & " controller to send the " & _
                 "selected message." & vbcrlf & _
                 "If the selected message object is a TRANSMIT OBJECT then " & _
                 "this function triggers the sending of a data frame. " & _
                 "If however the selected message object is a RECEIVE OBJECT " & _
                 "this function triggers the sending of a remote frame."
        
  sReturnValue = "None"
  If (Not func.AddFunction(sVarPre & "_NAME_" & sFctName, "void", sDescription, sReturnValue, 1)) Then Exit Function
    sDescription = "Number of the message object (1-14)"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para1", "ubObjNr", "ubyte", sDescription)) Then Exit Function
 
  '------------------------------------------------------------------------------------------------
  ' Description for CANx_NAME_...
  '------------------------------------------------------------------------------------------------
  sFctName = "ConfigMsgObj"
  sDescription = "This function sets up the message objects. This includes " & _
                 "the 8 data bytes, the identifier (11- or 29-bit), the data " & _
                 "number (0-8 bytes) and the XTD-bit. " & vbcrlf & _
                 "The message is not sent; for this the function " & _
                 r.v(sVarPre & "_NAME_Transmit") & " must be called." & vbcrlf & _
                 "" & vbcrlf & _
                 "The structure of the SW message object is defined in the " & _
                 "header file " & r.v(sVarPre & "_HFILE") & " (see T" & sVarPre & "_Obj)."
        
  sReturnValue = "None"
  If (Not func.AddFunction(sVarPre & "_NAME_" & sFctName, "void", sDescription, sReturnValue, 1)) Then Exit Function
    sDescription = "Number of the message object to be configured (1-15)"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para1", "ubObjNr", "ubyte", sDescription)) Then Exit Function
    sDescription = "Pointer on a message object"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para2", "*pstObj", "T" & sVarPre & "_Obj", sDescription)) Then Exit Function
 
  '------------------------------------------------------------------------------------------------
  ' Description for CANx_NAME_...
  '------------------------------------------------------------------------------------------------
  sFctName = "LoadData"
  sDescription = "If a hardware TRANSMIT OBJECT has to be loaded with data " & _
                 "but not with a new identifier, this function may be used " & _
                 "instead of the function " & r.v(sVarPre & "_NAME_ConfigMsgObj") & ". " & _
                 "The message object should be accessed by calling the function " & _
                 r.v(sVarPre & "_NAME_RequestMsgObj") & " before calling this function. This " & _
                 "prevents the " & sVarPre & " controller from working with invalid data."

  sReturnValue = "None"
  If (Not func.AddFunction(sVarPre & "_NAME_" & sFctName, "void", sDescription, sReturnValue, 1)) Then Exit Function
    sDescription = "Number of the message object to be configured (1-15)"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para1", "ubObjNr", "ubyte", sDescription)) Then Exit Function
    sDescription = "Pointer on a data buffer"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para2", "*pubData", "ubyte", sDescription)) Then Exit Function
 
  '------------------------------------------------------------------------------------------------
  ' Description for CANx_NAME_...
  '------------------------------------------------------------------------------------------------
  sFctName = "MsgLost"
  sDescription = "If a RECEIVE OBJECT receives new data before the old object " & _
                 "has been read, the old object is lost. The " & sVarPre & " controller " & _
                 "indicates this by setting the message lost bit (MSGLST). " & _
                 "This function returns the status of this bit. " & vbcrlf & _
                 "" & vbcrlf & _
                 "Note:" & vbcrlf & _
                 "This function resets the message lost bit (MSGLST)."
        
  sReturnValue = "1 the message object has lost a message, else 0"
  If (Not func.AddFunction(sVarPre & "_NAME_" & sFctName, "ubyte", sDescription, sReturnValue, 1)) Then Exit Function
    sDescription = "Number of the message object (1-15)"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para1", "ubObjNr", "ubyte", sDescription)) Then Exit Function
 
  '------------------------------------------------------------------------------------------------
  ' Description for CANx_NAME_...
  '------------------------------------------------------------------------------------------------
  sFctName = "DelMsgObj"
  sDescription = "This function marks the selected message object as not valid. " & _
                 "This means that this object cannot be sent or received. " & _
                 "If the selected object is busy (meaning the object is " & _
                 "transmitting a message or has received a new message) this " & _
                 "function returns the value ""0"" and the object is not deleted."
        
  sReturnValue = "1 the message object was deleted, else 0"
  If (Not func.AddFunction(sVarPre & "_NAME_" & sFctName, "ubyte", sDescription, sReturnValue, 1)) Then Exit Function
    sDescription = "Number of the message object (1-15)"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para1", "ubObjNr", "ubyte", sDescription)) Then Exit Function
 
  '------------------------------------------------------------------------------------------------
  ' Description for CANx_NAME_...
  '------------------------------------------------------------------------------------------------
  sFctName = "ReleaseObj"
  sDescription = "This function resets the NEWDAT flag of the selected RECEIVE " & _
                 "OBJECT, so that the " & sVarPre & " controller have access to it. " & _
                 "This function must be called if the function " & r.v(sVarPre & "_NAME_NewData") & _
                 " detects, that new data are present in the message object and " & _
                 "the actual data have been read by calling the function " & _
                 r.v(sVarPre & "_NAME_GetMsgObj") & ". "

  sReturnValue = "None"
  If (Not func.AddFunction(sVarPre & "_NAME_" & sFctName, "void", sDescription, sReturnValue, 1)) Then Exit Function
    sDescription = "Number of the message object (1-15)"
    If (Not func.AddParameter(sVarPre & "_NAME_" & sFctName & "_Para1", "ubObjNr", "ubyte", sDescription)) Then Exit Function
 

 	If (Not func.Sort) Then Exit Function

  RefreshFunctionDescriptions = True
End Function

'*****************************************************************************
'Description:
'        For each parameter that should be used as a constant (on page "Parameters")  
'        a line "If (Not func.AddParameter .." must be insert in this function.
'
'        Note:
'        For each added parameter a project variable with the name 
'        "DUMMY_PARA_Parametername" must be exist in the *.vars file. 
'-----------------------------------------------------------------------------
'Parameters:
'        vIndex           parameter of the module which was added with AddModule
'        func             reference to the FunctionClass object
'        r                reference to the Registers object
'-----------------------------------------------------------------------------
'Returns:
'        True            on successfull operation
'        False           else
'*****************************************************************************
Public Function RefreshParameterDescriptions(vIndex As Variant, para As ParameterClass, r As ProjectData) As Boolean
  On Error Resume Next 

  RefreshParameterDescriptions = False

  Dim sDescription As String
  Dim sVarPre As String
  Dim sRegPre As String
  Dim sParaName As String
  Dim i As Integer

  sVarPre = "CAN" & vIndex
  sRegPre = "C" & vIndex



  ' for each parameter of this module the property AddParameter must be called
  '
  ' AddParameter(sParameterName As String, sParameterDescription As String) As Boolean
  '
  ' sParameterName         | String | parameter name as key (use the name of the variable 
  '                                   for the parameter name e.g. SSC_PARA_MODE) 
  ' sParameterDescription  | String | description of the parameter

'  '------------------------------------------------------------------------------------------------
'  ' Description for DUMMY_PARA_xx
'  '------------------------------------------------------------------------------------------------
'  sDescription = "This parameter identifies CAN" & vIndex & " timer " & iTmr_x
'  sParaName = "TIMER_" & iTmr_x
'  If (Not para.AddParameter(sVarPre & "_PARA_" & sParaName, sDescription)) Then Exit Function
'
'  '------------------------------------------------------------------------------------------------
'  ' Description for DUMMY_PARA_xx
'  '------------------------------------------------------------------------------------------------
'  sDescription = "This parameter identifies CAN" & vIndex & " timer " & iTmr_y
'  sParaName = "TIMER_" & iTmr_y
'  If (Not para.AddParameter(sVarPre & "_PARA_" & sParaName, sDescription)) Then Exit Function
'
'  For i = iCh_low To iCh_high
'      '------------------------------------------------------------------------------------------------
'      ' Description for DUMMY_PARA_xx
'      '------------------------------------------------------------------------------------------------
'      sDescription = "This parameter identifies CAN" & vIndex & " register " & i
'      sParaName = "CC_" & i
'      If (Not para.AddParameter(sVarPre & "_PARA_" & sParaName, sDescription)) Then Exit Function
'  Next i
 	
 	If (Not para.Sort) Then Exit Function

  RefreshParameterDescriptions = True
End Function



'*****************************************************************************
'Description:
'          This function returns the module clock [MHz] of the 
'          CAN module depending on the configured modes
'-----------------------------------------------------------------------------
'Parameters:
'        r                reference to the Registers object
'        vIndex           ParameterValue
'-----------------------------------------------------------------------------
'Returns:
'      GetCANSystemClock [MHz]
'
'*****************************************************************************
Function GetCANModuleClock(r As ProjectData, vIndex As Variant) As Double
  On Error Resume Next
  Dim sVarPre As String
  Dim sRegPre As String
  Dim v As String
  
  sVarPre = "CAN" & vIndex
  sRegPre = "C" & vIndex
  GetCANModuleClock = GetSystemClock(r) 
End Function

'*****************************************************************************
'Description:
'        This function returns a formated disabled tooltip if the module
'        clock is disabled.
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          parameter
'-----------------------------------------------------------------------------
'Returns:
'        Formated tooltip
'*****************************************************************************
Function GetTooltipModuleDisabled(r As ProjectData, vIndex As Variant) As String
  On Error Resume Next
  Dim sVarPre As String

  sVarPre = "CAN" & vIndex
  
  GetTooltipModuleDisabled = ""            
  GetTooltipModuleDisabled =  GetTooltipModuleDisabled & FormatDisabledToolTip("the " & sVarPre & " module is disabled")
End Function

'*****************************************************************************
'Description:
'        This function returns the disable bit name of SYSCON3 register (e.g SSCDIS).
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          ParameterValue
'
'-----------------------------------------------------------------------------
'Returns:
'       disable bit name
'*****************************************************************************
Function GetCANDisebleBitName(r As ProjectData, vIndex As Variant) As String
    On Error Resume Next
    Dim sRegPre As String
    sRegPre = "CAN" & vIndex

    If (r.Regs.BitFind("SYSCON3_" & sRegPre & "DIS") = True) Then
        GetCANDisebleBitName = sRegPre & "DIS"
    Else
        GetCANDisebleBitName = ""
    End If


End Function


'*****************************************************************************
'Description:
'        This function check  the SYSCON3 register, whether the modul is disabled
'-----------------------------------------------------------------------------
'Parameters:
'        r               As ProjectData
'        vIndex          ParameterValue
'-----------------------------------------------------------------------------
'Returns:
'        True  -  if the modul is disabled
'        False -  else
'
'*****************************************************************************
Function IsModuleDisabled(r As ProjectData, vIndex As Variant) As Boolean

  IsModuleDisabled = False

  If (r.Regs.SfrFind("XPERCON") = True) Then
      If (r.v("SYSCON3_" & GetCANDisebleBitName(r, vIndex)) = 1 Or r.v("XPERCON_XPER" & vIndex - 1) = 0) Then
        IsModuleDisabled = True
      End If
  Else
      If (r.v("SYSCON3_" & GetCANDisebleBitName(r, vIndex)) = 1) Then
        IsModuleDisabled = True
      End If
  End If

End Function


'*****************************************************************************
'Description:
'        This function check the pininterface of CANx.
'-----------------------------------------------------------------------------
'Parameters:
'        r               As ProjectData
'        vIndex          ParameterValue
'        iBitNr          bit number of the bitfeld IPC
'-----------------------------------------------------------------------------
'Returns:
'        True  -  if pininterface free
'        False -  else
'
'*****************************************************************************
Function IsPinInterfaceFree(r As ProjectData, vIndex As Variant, iBitNr As Integer) As Boolean
    On Error Resume Next
    Dim sModIndex As String
    Dim sVarPre As String
    sVarPre = "CAN" & vIndex

    IsPinInterfaceFree = False

    If (vIndex = 1) Then
        sModIndex = "CAN" & 2 'if sVarPre = CAN1 then sModIndex = CAN2
    Else
        sModIndex = "CAN" & 1 'if sVarPre = CAN2 then sModIndex = CAN1
    End If
    
    Select Case iBitNr
        Case 0
            If (vIndex = 1) Then
                If (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_1")) Or (Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_1")) And GetPinFunction(r, sVarPre & "_TxD_1") <> 2 And GetPinFunction(r, sModIndex & "_TxD_1") <> 2)) Then
                    IsPinInterfaceFree = False
                Else
                    IsPinInterfaceFree = True
                End If
            Else
                If (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_1")) Or (Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_0")) And GetPinFunction(r, sVarPre & "_RxD_0") <> 1) Or GetPinFunction(r, sModIndex & "_RxD_0") = 1) Then
                    IsPinInterfaceFree = False
                Else
                    IsPinInterfaceFree = True
                End If
            End If

        Case 1
            If (vIndex = 1) Then
                If ( (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_0")) And GetPinFunction(r, sModIndex & "_RxD_0") <> 1) Or  (Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_1")) And GetPinFunction(r, sModIndex & "_TxD_1") <> 2 And GetPinFunction(r, sVarPre & "_TxD_1") <> 2) ) Then
                    IsPinInterfaceFree = False
                Else
                    IsPinInterfaceFree = True
                End If
            Else
                If ( (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_0")) And GetPinFunction(r, sModIndex & "_RxD_0") <> 1 And GetPinFunction(r, sVarPre & "_TxD_0") <> 2) Or (Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_1")) And GetPinFunction(r, sModIndex & "_TxD_1") <> 2) ) Then
                    IsPinInterfaceFree = False
                Else
                    IsPinInterfaceFree = True
                End If
            End If
            
        Case 2
            If ( (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_2")) And GetPinFunction(r, sModIndex & "_RxD_2") = 0) Or  (Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_2")) And GetPinFunction(r, sModIndex & "_TxD_2") = 0) ) Then
                IsPinInterfaceFree = False
            Else
                IsPinInterfaceFree = True
            End If

        Case 3
            If ( (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_3")) And GetPinFunction(r, sModIndex & "_RxD_3") = 0) Or  (Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_3")) And GetPinFunction(r, sModIndex & "_TxD_3") = 0) ) Then
                IsPinInterfaceFree = False
            Else
                IsPinInterfaceFree = True
            End If

    End Select

End Function 


'*****************************************************************************
'Description:
'        This function returns a formated disabled tooltip if the pininterface
'        is not free.
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          parameter
'        iBitNr          bit number of the bitfeld IPC
'-----------------------------------------------------------------------------
'Returns:
'        Formated tooltip
'*****************************************************************************
Function GetTooltipPinInterfaceNotFree(r As ProjectData, vIndex As Variant, iBitNr As Integer) As String
    On Error Resume Next
    Dim sVarPre As String
    Dim sModIndex As String   
    Dim s As String
    sVarPre = "CAN" & vIndex

    If (vIndex = 1) Then
        sModIndex = "CAN" & 2 'if sVarPre = CAN1 then sModIndex = CAN2
    Else
        sModIndex = "CAN" & 1 'if sVarPre = CAN2 then sModIndex = CAN1
    End If

    GetTooltipPinInterfaceNotFree = ""
    s = ""

    Select Case iBitNr
        Case 0
            If (vIndex = 1) Then
                If (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_1"))) Then
                    s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_RxD_1")
                End If
                If (Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_1")) And GetPinFunction(r, sVarPre & "_TxD_1") <> 2 And GetPinFunction(r, sModIndex & "_TxD_1") <> 2) Then
                    s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_TxD_1")
                End If
            Else
                If (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_1"))) Then
                    s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_RxD_1")
                End If
                If ((Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_0")) And GetPinFunction(r, sVarPre & "_RxD_0") <> 1) Or GetPinFunction(r, sModIndex & "_RxD_0") = 1) Then
                    s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_TxD_0")
                End If
            End If
        Case 1
            If (vIndex = 1) Then
                If (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_0")) And GetPinFunction(r, sModIndex & "_RxD_0") <> 1) Then
                    s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_RxD_0")
                End If
                If (Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_1")) And GetPinFunction(r, sModIndex & "_TxD_1") <> 2 And GetPinFunction(r, sVarPre & "_TxD_1") <> 2) Then
                    s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_TxD_1")
                End If
            Else
                If (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_0")) And GetPinFunction(r, sModIndex & "_RxD_0") <> 1 And GetPinFunction(r, sVarPre & "_TxD_0") <> 2) Then
                    s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_RxD_0")
                End If
                If (Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_1")) And GetPinFunction(r, sModIndex & "_TxD_1") <> 2) Then
                    s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_TxD_1")
                End If
            End If

        Case 2
            If (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_2")) And GetPinFunction(r, sModIndex & "_RxD_2") = 0) Then
                s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_RxD_2")
            End If
            If (Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_2")) And GetPinFunction(r, sModIndex & "_TxD_2") = 0) Then
                s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_TxD_2")
            End If

        Case 3
            If (Not(IsAlternateInputPinFree(r, sVarPre & "_RxD_3")) And GetPinFunction(r, sModIndex & "_RxD_3") = 0) Then
                s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_RxD_3")
            End If
            If (Not(IsAlternateOutputPinFree(r, sVarPre & "_TxD_3")) And GetPinFunction(r, sModIndex & "_TxD_3") = 0) Then
                s = s & GetDisabledAlternatePinTooltip(r, sVarPre & "_TxD_3")
            End If

    End Select


    GetTooltipPinInterfaceNotFree = s

End Function



'*****************************************************************************
'Description:
'        This function set the pininterface of CANx. 
'
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          parameter
'        iBitNr          bit number of the bitfeld IPC
'-----------------------------------------------------------------------------
'Returns:
'
'*****************************************************************************
Sub  SetCANPinInterface(r As ProjectData, vIndex As Variant, iBitNr As Integer)
    On Error Resume Next
    Dim sVarPre As String
    Dim sModIndex As String   
    sVarPre = "CAN" & vIndex

    If (vIndex = 1) Then
        sModIndex = "CAN" & 2 'if sVarPre = CAN1 then sModIndex = CAN2
    Else
        sModIndex = "CAN" & 1 'if sVarPre = CAN2 then sModIndex = CAN1
    End If

    Select Case iBitNr
        Case 0
            If (GetPinFunction(r, sVarPre & "_RxD_0") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_0")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_1") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_1")
                If (GetPinFunction(r, sModIndex & "_TxD_1") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_1")
                End If
            End If

            If (GetPinFunction(r, sVarPre & "_RxD_2") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_2")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_2") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_2")
                If (GetPinFunction(r, sModIndex & "_TxD_2") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_2")
                End If
            End If

            If (GetPinFunction(r, sVarPre & "_RxD_3") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_3")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_3") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_3")
                If (GetPinFunction(r, sModIndex & "_TxD_3") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_3")
                End If
            End If

            If (vIndex = 1) Then
                Call RequestAlternateInputPin(r, sVarPre & "_RxD_1")
                Call RequestAlternateOutputPin(r, sVarPre & "_TxD_1")
            Else
                Call RequestAlternateInputPin(r, sVarPre & "_RxD_1")
                Call RequestAlternateOutputPin(r, sVarPre & "_TxD_0")
            End If

        Case 1
            If (vIndex = 1) Then
                If (GetPinFunction(r, sVarPre & "_RxD_1") = 1) Then
                    Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_1")
                End If
                If (GetPinFunction(r, sVarPre & "_TxD_1") = 2) Then
                    Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_1")
                    If (GetPinFunction(r, sModIndex & "_TxD_1") = 2) Then
                        Call RequestAlternateOutputPin(r, sModIndex & "_TxD_1")
                    End If
                End If
            Else
                If (GetPinFunction(r, sVarPre & "_RxD_1") = 1) Then
                    Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_1")
                End If
                If (GetPinFunction(r, sVarPre & "_TxD_0") = 2) Then
                    Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_0")
                    If (GetPinFunction(r, sModIndex & "_TxD_1") = 2) Then
                        Call RequestAlternateOutputPin(r, sModIndex & "_TxD_1")
                    End If
                End If
            End If

            If (GetPinFunction(r, sVarPre & "_RxD_2") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_2")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_2") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_2")
                If (GetPinFunction(r, sModIndex & "_TxD_2") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_2")
                End If
            End If

            If (GetPinFunction(r, sVarPre & "_RxD_3") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_3")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_3") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_3")
                If (GetPinFunction(r, sModIndex & "_TxD_3") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_3")
                End If
            End If

            Call RequestAlternateInputPin(r, sVarPre & "_RxD_0")
            Call RequestAlternateOutputPin(r, sVarPre & "_TxD_1")

        Case 2
            If (vIndex = 1) Then
                If (GetPinFunction(r, sVarPre & "_RxD_1") = 1) Then
                    Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_1")
                End If
                If (GetPinFunction(r, sVarPre & "_TxD_1") = 2) Then
                    Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_1")
                    If (GetPinFunction(r, sModIndex & "_TxD_1") = 2) Then
                        Call RequestAlternateOutputPin(r, sModIndex & "_TxD_1")
                    End If
                End If
            Else
                If (GetPinFunction(r, sVarPre & "_RxD_1") = 1) Then
                    Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_1")
                End If
                If (GetPinFunction(r, sVarPre & "_TxD_0") = 2) Then
                    Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_0")
                End If
            End If

            If (GetPinFunction(r, sVarPre & "_RxD_0") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_0")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_1") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_1")
                If (GetPinFunction(r, sModIndex & "_TxD_1") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_1")
                End If
            End If

            If (GetPinFunction(r, sVarPre & "_RxD_3") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_3")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_3") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_3")
                If (GetPinFunction(r, sModIndex & "_TxD_3") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_3")
                End If
            End If

            Call RequestAlternateInputPin(r, sVarPre & "_RxD_2")
            Call RequestAlternateOutputPin(r, sVarPre & "_TxD_2")

        Case 3
            If (vIndex = 1) Then
                If (GetPinFunction(r, sVarPre & "_RxD_1") = 1) Then
                    Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_1")
                End If
                If (GetPinFunction(r, sVarPre & "_TxD_1") = 2) Then
                    Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_1")
                    If (GetPinFunction(r, sModIndex & "_TxD_1") = 2) Then
                        Call RequestAlternateOutputPin(r, sModIndex & "_TxD_1")
                    End If
                End If
            Else
                If (GetPinFunction(r, sVarPre & "_RxD_1") = 1) Then
                    Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_1")
                End If
                If (GetPinFunction(r, sVarPre & "_TxD_0") = 2) Then
                    Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_0")
                End If
            End If

            If (GetPinFunction(r, sVarPre & "_RxD_0") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_0")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_1") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_1")
                If (GetPinFunction(r, sModIndex & "_TxD_1") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_1")
                End If
            End If

            If (GetPinFunction(r, sVarPre & "_RxD_2") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_2")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_2") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_2")
                If (GetPinFunction(r, sModIndex & "_TxD_2") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_2")
                End If
            End If

            Call RequestAlternateInputPin(r, sVarPre & "_RxD_3")
            Call RequestAlternateOutputPin(r, sVarPre & "_TxD_3")

        Case 7
            If (vIndex = 1) Then
                If (GetPinFunction(r, sVarPre & "_RxD_1") = 1) Then
                    Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_1")
                End If
                If (GetPinFunction(r, sVarPre & "_TxD_1") = 2) Then
                    Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_1")
                    If (GetPinFunction(r, sModIndex & "_TxD_1") = 2) Then
                        Call RequestAlternateOutputPin(r, sModIndex & "_TxD_1")
                    End If
                End If
            Else
                If (GetPinFunction(r, sVarPre & "_RxD_1") = 1) Then
                    Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_1")
                End If
                If (GetPinFunction(r, sVarPre & "_TxD_0") = 2) Then
                    Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_0")
                End If
            End If

            If (GetPinFunction(r, sVarPre & "_RxD_0") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_0")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_1") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_1")
                If (GetPinFunction(r, sModIndex & "_TxD_1") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_1")
                End If
            End If

            If (GetPinFunction(r, sVarPre & "_RxD_2") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_2")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_2") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_2")
                If (GetPinFunction(r, sModIndex & "_TxD_2") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_2")
                End If
            End If

            If (GetPinFunction(r, sVarPre & "_RxD_3") = 1) Then
                Call ReleaseAlternateInputPin(r, sVarPre & "_RxD_3")
            End If
            If (GetPinFunction(r, sVarPre & "_TxD_3") = 2) Then
                Call ReleaseAlternateOutputPin(r, sVarPre & "_TxD_3")
                If (GetPinFunction(r, sModIndex & "_TxD_3") = 2) Then
                    Call RequestAlternateOutputPin(r, sModIndex & "_TxD_3")
                End If
            End If

    End Select


End Sub




'*****************************************************************************
'Description:
'        This function returns the min value of bit TSEG1.
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          ParameterValue
'        vValue          input value
'
'-----------------------------------------------------------------------------
'Returns:
'       min value of TSEG1
'*****************************************************************************
Function GetMinTseg1Value(r As ProjectData, vIndex As Variant, vValue As Variant) As Integer
    On Error Resume Next
    Dim sVarPre As String
    Dim sRegPre As String
    Dim iMin As Integer
    sVarPre = "CAN" & vIndex
    sRegPre = "C" & vIndex
    iMin = r.d(sRegPre & "BTR_SJW") + 1

    If (vValue < iMin) Then
        If (vValue < 3) Then
            GetMinTseg1Value = 3
        Else
            GetMinTseg1Value = r.d(sRegPre & "BTR_SJW") + 1
        End If
    Else
        GetMinTseg1Value = 3
    End If


End Function

'*****************************************************************************
'Description:
'        This function returns the min value of bit TSEG2.
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          ParameterValue
'        vValue          input value
'
'-----------------------------------------------------------------------------
'Returns:
'       min value of TSEG2
'*****************************************************************************
Function GetMinTseg2Value(r As ProjectData, vIndex As Variant, vValue As Variant) As Integer
    On Error Resume Next
    Dim sVarPre As String
    Dim sRegPre As String
    Dim iMin As Integer
    sVarPre = "CAN" & vIndex
    sRegPre = "C" & vIndex
    iMin = r.d(sRegPre & "BTR_SJW") + 1

    If (vValue < iMin) Then
        If (vValue < 2) Then
            GetMinTseg2Value = 2
        Else
            GetMinTseg2Value = r.d(sRegPre & "BTR_SJW") + 1
        End If
    Else
        GetMinTseg2Value = 2
    End If


End Function


'*****************************************************************************
'Description:
'        This function returns the min value of bit SJW.
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          ParameterValue
'        vValue          input value
'
'-----------------------------------------------------------------------------
'Returns:
'       min value of SJW
'*****************************************************************************
Function GetMinSJWValue(r As ProjectData, vIndex As Variant, vValue As Variant) As Integer
    On Error Resume Next
    Dim sVarPre As String
    Dim sRegPre As String
    sVarPre = "CAN" & vIndex
    sRegPre = "C" & vIndex

    GetMinSJWValue = 1

End Function

'*****************************************************************************
'Description:
'        This function returns the max value of bit SJW.
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          ParameterValue
'        vValue          input value
'
'-----------------------------------------------------------------------------
'Returns:
'       max value of SJW
'*****************************************************************************
Function GetMaxSJWValue(r As ProjectData, vIndex As Variant, vValue As Variant) As Integer
    On Error Resume Next
    Dim sVarPre As String
    Dim sRegPre As String
    sVarPre = "CAN" & vIndex
    sRegPre = "C" & vIndex

    If (( (vValue - 1) > r.d(sRegPre & "BTR_TSEG1")) Or ( (vValue - 1) > r.d(sRegPre & "BTR_TSEG2") )) Then
        If (vValue > 4) Then
            GetMaxSJWValue = 4
        Else
            If (vValue > (r.d(sRegPre & "BTR_TSEG1") + 1)) Then
                GetMaxSJWValue = r.d(sRegPre & "BTR_TSEG1") + 1
            End If
            If (vValue > (r.d(sRegPre & "BTR_TSEG2") + 1)) Then
                GetMaxSJWValue = r.d(sRegPre & "BTR_TSEG2") + 1
            End If
        End If
    Else
        GetMaxSJWValue = 4
    End If


End Function


'*****************************************************************************
'Description:
'        This function returns the min required baud rate [Baud].
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          ParameterValue
'
'-----------------------------------------------------------------------------
'Returns:
'       min required baud rate [Baud]
'*****************************************************************************
Function GetMinReqBR(r As ProjectData, vIndex As Variant) As Long
    On Error Resume Next
    Dim sVarPre As String
    Dim sRegPre As String
    sVarPre = "CAN" & vIndex
    sRegPre = "C" & vIndex

    GetMinReqBR = GetCANModuleClock(r, vIndex) * 1000000 / (64 * 2^(1 - r.d(sRegPre & "CSR_CPS")) * _
                  (3 + r.d(sRegPre & "BTR_TSEG1") + r.d(sRegPre & "BTR_TSEG2")) )

End Function

'*****************************************************************************
'Description:
'        This function returns the max required baud rate [Baud].
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          ParameterValue
'
'-----------------------------------------------------------------------------
'Returns:
'       max required baud rate [Baud]
'*****************************************************************************
Function GetMaxReqBR(r As ProjectData, vIndex As Variant) As Long
    On Error Resume Next
    Dim sVarPre As String
    Dim sRegPre As String
    sVarPre = "CAN" & vIndex
    sRegPre = "C" & vIndex

    GetMaxReqBR = GetCANModuleClock(r, vIndex) * 1000000 / (2^(1 - r.d(sRegPre & "CSR_CPS")) * _
                  (3 + r.d(sRegPre & "BTR_TSEG1") + r.d(sRegPre & "BTR_TSEG2")) )

End Function


'*****************************************************************************
'Description:
'        This function updates the CANx module
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          ParameterValue
'
'-----------------------------------------------------------------------------
'Returns:
'       none
'*****************************************************************************
Sub UpdateCAN(r As ProjectData, vIndex As Variant)
    On Error Goto UpdateCANError
    Dim sVarPre As String
    Dim sRegPre As String
    sVarPre = "CAN" & vIndex
    sRegPre = "C" & vIndex

    If (r.v(sVarPre & "_Baudrate") > GetMaxReqBR(r, vIndex)) Then
        r.v(sVarPre & "_Baudrate") = GetMaxReqBR(r, vIndex)
    End If
    If (r.v(sVarPre & "_Baudrate") < GetMinReqBR(r, vIndex)) Then
        r.v(sVarPre & "_Baudrate") = GetMinReqBR(r, vIndex)
    End If

    r.l(sRegPre & "BTR_BRP") = (1000000 * GetCANModuleClock(r, vIndex) / (r.v(sVarPre & "_Baudrate") * _
                               2^(1 - r.d(sRegPre & "CSR_CPS")) * (3 + r.d(sRegPre & "BTR_TSEG1") + _
                               r.d(sRegPre & "BTR_TSEG2")) ) - 1)
    Exit Sub

UpdateCANError:
    r.d(sRegPre & "BTR_BRP") = 10
    Exit Sub

End Sub



'*****************************************************************************
'Description:
'        This function sets all objects to the default.
'-----------------------------------------------------------------------------
'Parameters:
'        r               reference to the ProjectData object
'        vIndex          ParameterValue
'
'-----------------------------------------------------------------------------
'Returns:
'       none
'*****************************************************************************
Sub SetAllObjectsToDefault(r As ProjectData, vIndex As Variant)
    Dim sVarPre As String
    Dim sRegPre As String
    Dim iObj As Integer
    sVarPre = "CAN" & vIndex
    sRegPre = "C" & vIndex

    For iObj = 1 To 14

        If (r.v(sRegPre & "MCR" & iObj & "_MSGVAL") <> 1) Then
            r.v(sRegPre & "MCR" & iObj & "_MSGVAL") = 1
            r.v(sRegPre & "MCR" & iObj & "_RXIE") = 1
            r.v(sRegPre & "MCR" & iObj & "_TXIE") = 1
        End If

    Next iObj
    
    r.v(sRegPre & "MCR15_MSGVAL") = 1
    r.v(sRegPre & "MCR15_RXIE") = 1


End Sub
